mirror of
https://github.com/osmarks/ngircd.git
synced 2024-12-12 01:40:27 +00:00
Merge branch 'bug145-ProvideHelp'
* bug145-ProvideHelp: Use "${docdir}/Commands.txt" as help text file Add a note that "help file" is updated on startup and REHASH only Add doc/Commands.txt which should document all commands Implement Help() function parsing and returning the help text Document "HelpFile" in sample-ngircd.conf and ngircd.conf.5 Implement new configuration option "HelpFile" IRC_HELP(): Code cleanup Refactor Read_Motd() into Read_TextFile()
This commit is contained in:
commit
68cb1a8c2e
@ -1,6 +1,6 @@
|
||||
#
|
||||
# ngIRCd -- The Next Generation IRC Daemon
|
||||
# Copyright (c)2001-2012 Alexander Barton (alex@barton.de) and Contributors
|
||||
# Copyright (c)2001-2013 Alexander Barton (alex@barton.de) and Contributors
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
@ -110,7 +110,7 @@ esac
|
||||
# Add additional CFLAGS, eventually specified on the command line:
|
||||
test -n "$CFLAGS_ADD" && CFLAGS="$CFLAGS $CFLAGS_ADD"
|
||||
|
||||
CFLAGS="$CFLAGS -DSYSCONFDIR='\"\$(sysconfdir)\"'"
|
||||
CFLAGS="$CFLAGS -DSYSCONFDIR='\"\$(sysconfdir)\"' -DDOCDIR='\"\$(docdir)\"'"
|
||||
|
||||
# -- Headers --
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* ngIRCd -- The Next Generation IRC Daemon
|
||||
* Copyright (c)2001-2012 Alexander Barton (alex@barton.de) and Contributors.
|
||||
* Copyright (c)2001-2013 Alexander Barton (alex@barton.de) and Contributors.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -17,6 +17,7 @@
|
||||
#define VERSION "??("__DATE__")"
|
||||
#endif
|
||||
#define SYSCONFDIR "/etc/ngircd"
|
||||
#define DOCDIR "/usr/share/doc/ngircd"
|
||||
|
||||
#ifndef TARGET_VENDOR
|
||||
#define TARGET_VENDOR "apple"
|
||||
|
219
doc/Commands.txt
Normal file
219
doc/Commands.txt
Normal file
@ -0,0 +1,219 @@
|
||||
|
||||
ngIRCd - Next Generation IRC Server
|
||||
http://ngircd.barton.de/
|
||||
|
||||
(c)2001-2013 Alexander Barton and Contributors.
|
||||
ngIRCd is free software and published under the
|
||||
terms of the GNU General Public License.
|
||||
|
||||
-- Commands.txt --
|
||||
|
||||
|
||||
This file lists all commands available on ngIRCd. It is written in a format
|
||||
that is human readable as well as machine parseable and therefore can be used
|
||||
as "help text file" of the daemon.
|
||||
|
||||
In short, the HELP command parses this file as following when a user user
|
||||
issues a "HELP <cmd>" command:
|
||||
|
||||
1. Search the file for a line "- <cmd>",
|
||||
2. Output all subsequent lines that start with a TAB (ASCII 9) character
|
||||
to the client using NOTICE commands, treat lines containing a single "."
|
||||
after the TAB as empty lines.
|
||||
3. Break at the first line not starting with a TAB character.
|
||||
|
||||
This format allows to have information to each command stored in this file
|
||||
which will not be sent to an IRC user requesting help which enables us to
|
||||
have additional annotations stored here which further describe the origin,
|
||||
implementation details, or limits of the specific command.
|
||||
|
||||
A special "Intro" block is returned to the user when the HELP command is
|
||||
used without a command name:
|
||||
|
||||
|
||||
- Intro
|
||||
This is ngIRCd, a server software for Internet Relay Chat (IRC)
|
||||
networks. You can find more information about ngIRCd on its homepage:
|
||||
<http://ngircd.barton.de>
|
||||
.
|
||||
Use "HELP COMMANDS" to get a list of all available commands and
|
||||
"HELP <command-name>" to get help for a specific IRC command, for
|
||||
example "HELP quit" or "HELP privmsg".
|
||||
|
||||
|
||||
General Commands
|
||||
~~~~~~~~~~~~~~~~
|
||||
|
||||
- AWAY
|
||||
|
||||
- CAP
|
||||
|
||||
- CHARCONV
|
||||
|
||||
- HELP
|
||||
HELP [<command>]
|
||||
.
|
||||
Show help information for a specific IRC <command>. The <command> name
|
||||
is case-insensitive.
|
||||
.
|
||||
Use the command "HELP Commands" to get a list of all available commands.
|
||||
|
||||
The HELP command isn't specified by any RFC but implemented by most
|
||||
daemons. If no help text could be read in, ngIRCd outputs a list of all
|
||||
implemented commands when receiving a plain "HELP" command as well as
|
||||
on "HELP Commands".
|
||||
|
||||
ngIRCd replies using "NOTICE" commands like ircd 2.10/2.11; other
|
||||
implementations are using numerics 704, 705, and 706.
|
||||
|
||||
|
||||
- MODE
|
||||
|
||||
- NICK
|
||||
|
||||
- NOTICE
|
||||
|
||||
- PASS
|
||||
|
||||
- PING
|
||||
|
||||
- PONG
|
||||
|
||||
- PRIVMSG
|
||||
|
||||
- QUIT
|
||||
QUIT [<quit-message>]
|
||||
.
|
||||
End IRC session and disconnect from the server.
|
||||
.
|
||||
If a <quit-message> has been given, it is displayed to all the
|
||||
channels that you are a member of when leaving.
|
||||
|
||||
- USER
|
||||
|
||||
- WALLOPS
|
||||
|
||||
- WEBIRC
|
||||
|
||||
|
||||
Status and Informational Commands
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
- INFO
|
||||
|
||||
- ISON
|
||||
|
||||
- LINKS
|
||||
|
||||
- LUSERS
|
||||
|
||||
- METADATA
|
||||
|
||||
- MOTD
|
||||
|
||||
- NAMES
|
||||
|
||||
- STATS
|
||||
|
||||
- TIME
|
||||
|
||||
- TRACE
|
||||
|
||||
- USERHOST
|
||||
|
||||
- VERSION
|
||||
|
||||
- WHO
|
||||
|
||||
- WHOIS
|
||||
|
||||
- WHOWAS
|
||||
|
||||
|
||||
Channel Commands
|
||||
~~~~~~~~~~~~~~~~
|
||||
|
||||
- INVITE
|
||||
|
||||
- JOIN
|
||||
|
||||
- KICK
|
||||
|
||||
- LIST
|
||||
|
||||
- PART
|
||||
|
||||
- TOPIC
|
||||
|
||||
|
||||
Administrative Commands
|
||||
~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
- ADMIN
|
||||
ADMIN [<server>]
|
||||
.
|
||||
Show administartive information about an IRC server in the network.
|
||||
If no server name has been given, the local server will respond.
|
||||
|
||||
- CONNECT
|
||||
|
||||
- DIE
|
||||
|
||||
- DISCONNECT
|
||||
|
||||
- GLINE
|
||||
|
||||
- KILL
|
||||
|
||||
- KLINE
|
||||
|
||||
- OPER
|
||||
|
||||
- REHASH
|
||||
|
||||
- RESTART
|
||||
|
||||
|
||||
IRC Service Commands
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
- SERVICE
|
||||
|
||||
- SERVLIST
|
||||
|
||||
- SQUERY
|
||||
|
||||
- SVSNICK
|
||||
|
||||
|
||||
Server Protocol Commands
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
- CHANINFO
|
||||
|
||||
- ERROR
|
||||
ERROR [<message> [<> [...]]]
|
||||
.
|
||||
Return an error message to the server. The first parameter, if given,
|
||||
will be logged by the server, all further parameters are silently
|
||||
ignored.
|
||||
.
|
||||
This command is silently ignored on non-server and non-service links.
|
||||
|
||||
- NJOIN
|
||||
|
||||
- SERVER
|
||||
|
||||
- SQUIT
|
||||
|
||||
|
||||
Dummy Commands
|
||||
~~~~~~~~~~~~~~
|
||||
|
||||
- SUMMON
|
||||
|
||||
- USERS
|
||||
|
||||
- GET
|
||||
|
||||
- POST
|
@ -1,6 +1,6 @@
|
||||
#
|
||||
# ngIRCd -- The Next Generation IRC Daemon
|
||||
# Copyright (c)2001-2012 Alexander Barton (alex@barton.de) and Contributors
|
||||
# Copyright (c)2001-2013 Alexander Barton (alex@barton.de) and Contributors
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
@ -12,6 +12,7 @@
|
||||
.tmpl:
|
||||
$(AM_V_GEN)sed \
|
||||
-e "s@:ETCDIR:@${sysconfdir}@" \
|
||||
-e "s@:DOCDIR:@${docdir}@" \
|
||||
<$< >$@
|
||||
|
||||
SUFFIXES = .tmpl
|
||||
@ -19,6 +20,7 @@ SUFFIXES = .tmpl
|
||||
static_docs = \
|
||||
Bopm.txt \
|
||||
Capabilities.txt \
|
||||
Commands.txt \
|
||||
Contributing.txt \
|
||||
FAQ.txt \
|
||||
GIT.txt \
|
||||
|
@ -33,6 +33,10 @@
|
||||
;AdminInfo2 = Location
|
||||
;AdminEMail = admin@irc.server
|
||||
|
||||
# Text file which contains the ngIRCd help text. This file is required
|
||||
# to display help texts when using the "HELP <cmd>" command.
|
||||
;HelpFile = :DOCDIR:/Commands.txt
|
||||
|
||||
# Info text of the server. This will be shown by WHOIS and
|
||||
# LINKS requests for example.
|
||||
Info = Server Info Text
|
||||
|
@ -101,6 +101,12 @@ IRC network and must contain at least one dot (".") character.
|
||||
Information about the server and the administrator, used by the ADMIN
|
||||
command. This information is not required by the server but by RFC!
|
||||
.TP
|
||||
\fBHelpFile\fR (string)
|
||||
Text file which contains the ngIRCd help text. This file is required
|
||||
to display help texts when using the "HELP <cmd>" command.
|
||||
Please note: Changes made to this file take effect when ngircd starts up
|
||||
or is instructed to re-read its configuration file.
|
||||
.TP
|
||||
\fBInfo\fR (string)
|
||||
Info text of the server. This will be shown by WHOIS and LINKS requests for
|
||||
example.
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* ngIRCd -- The Next Generation IRC Daemon
|
||||
* Copyright (c)2001-2012 Alexander Barton (alex@barton.de) and Contributors.
|
||||
* Copyright (c)2001-2013 Alexander Barton (alex@barton.de) and Contributors.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -54,6 +54,7 @@ static CONF_SERVER New_Server;
|
||||
static int New_Server_Idx;
|
||||
|
||||
static char Conf_MotdFile[FNAME_LEN];
|
||||
static char Conf_HelpFile[FNAME_LEN];
|
||||
|
||||
static void Set_Defaults PARAMS(( bool InitServers ));
|
||||
static bool Read_Config PARAMS(( bool TestOnly, bool IsStarting ));
|
||||
@ -316,6 +317,7 @@ Conf_Test( void )
|
||||
printf(" AdminInfo1 = %s\n", Conf_ServerAdmin1);
|
||||
printf(" AdminInfo2 = %s\n", Conf_ServerAdmin2);
|
||||
printf(" AdminEMail = %s\n", Conf_ServerAdminMail);
|
||||
printf(" HelpFile = %s\n", Conf_HelpFile);
|
||||
printf(" Info = %s\n", Conf_ServerInfo);
|
||||
printf(" Listen = %s\n", Conf_ListenAddress);
|
||||
if (Using_MotdFile) {
|
||||
@ -701,8 +703,11 @@ Set_Defaults(bool InitServers)
|
||||
Conf_ListenAddress = NULL;
|
||||
array_free(&Conf_ListenPorts);
|
||||
array_free(&Conf_Motd);
|
||||
array_free(&Conf_Helptext);
|
||||
strlcpy(Conf_MotdFile, SYSCONFDIR, sizeof(Conf_MotdFile));
|
||||
strlcat(Conf_MotdFile, MOTD_FILE, sizeof(Conf_MotdFile));
|
||||
strlcpy(Conf_HelpFile, DOCDIR, sizeof(Conf_HelpFile));
|
||||
strlcat(Conf_HelpFile, HELP_FILE, sizeof(Conf_HelpFile));
|
||||
strcpy(Conf_ServerPwd, "");
|
||||
strlcpy(Conf_PidFile, PID_FILE, sizeof(Conf_PidFile));
|
||||
Conf_UID = Conf_GID = 0;
|
||||
@ -784,39 +789,44 @@ no_listenports(void)
|
||||
}
|
||||
|
||||
/**
|
||||
* Read MOTD ("message of the day") file.
|
||||
* Read contents of a text file into an array.
|
||||
*
|
||||
* This function is used to read the MOTD and help text file, for exampe.
|
||||
*
|
||||
* @param filename Name of the file to read.
|
||||
* @return true, when the file has been read in.
|
||||
*/
|
||||
static void
|
||||
Read_Motd(const char *filename)
|
||||
static bool
|
||||
Read_TextFile(const char *Filename, const char *Name, array *Destination)
|
||||
{
|
||||
char line[127];
|
||||
FILE *fp;
|
||||
int line_no = 1;
|
||||
|
||||
if (*filename == '\0')
|
||||
return;
|
||||
if (*Filename == '\0')
|
||||
return false;
|
||||
|
||||
fp = fopen(filename, "r");
|
||||
fp = fopen(Filename, "r");
|
||||
if (!fp) {
|
||||
Config_Error(LOG_WARNING, "Can't read MOTD file \"%s\": %s",
|
||||
filename, strerror(errno));
|
||||
return;
|
||||
Config_Error(LOG_WARNING, "Can't read %s file \"%s\": %s",
|
||||
Name, Filename, strerror(errno));
|
||||
return false;
|
||||
}
|
||||
|
||||
array_free(&Conf_Motd);
|
||||
Using_MotdFile = true;
|
||||
|
||||
array_free(Destination);
|
||||
while (fgets(line, (int)sizeof line, fp)) {
|
||||
ngt_TrimLastChr( line, '\n');
|
||||
ngt_TrimLastChr(line, '\n');
|
||||
|
||||
/* add text including \0 */
|
||||
if (!array_catb(&Conf_Motd, line, strlen(line) + 1)) {
|
||||
Log(LOG_WARNING, "Cannot add MOTD text: %s", strerror(errno));
|
||||
if (!array_catb(Destination, line, strlen(line) + 1)) {
|
||||
Log(LOG_WARNING, "Cannot read/add \"%s\", line %d: %s",
|
||||
Filename, line_no, strerror(errno));
|
||||
break;
|
||||
}
|
||||
line_no++;
|
||||
}
|
||||
fclose(fp);
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -1037,8 +1047,16 @@ Read_Config(bool TestOnly, bool IsStarting)
|
||||
}
|
||||
|
||||
/* No MOTD phrase configured? (re)try motd file. */
|
||||
if (array_bytes(&Conf_Motd) == 0)
|
||||
Read_Motd(Conf_MotdFile);
|
||||
if (array_bytes(&Conf_Motd) == 0) {
|
||||
if (Read_TextFile(Conf_MotdFile, "MOTD", &Conf_Motd))
|
||||
Using_MotdFile = true;
|
||||
}
|
||||
|
||||
/* Try to read ngIRCd help text file. */
|
||||
(void)Read_TextFile(Conf_HelpFile, "help text", &Conf_Helptext);
|
||||
if (!array_bytes(&Conf_Helptext))
|
||||
Config_Error(LOG_WARNING,
|
||||
"No help text available, HELP command will be of limited use.");
|
||||
|
||||
#ifdef SSL_SUPPORT
|
||||
/* Make sure that all SSL-related files are readable */
|
||||
@ -1305,6 +1323,12 @@ Handle_GLOBAL( int Line, char *Var, char *Arg )
|
||||
Config_Error_TooLong(Line, Var);
|
||||
return;
|
||||
}
|
||||
if (strcasecmp(Var, "HelpFile") == 0) {
|
||||
len = strlcpy(Conf_HelpFile, Arg, sizeof(Conf_HelpFile));
|
||||
if (len >= sizeof(Conf_HelpFile))
|
||||
Config_Error_TooLong(Line, Var);
|
||||
return;
|
||||
}
|
||||
if (strcasecmp(Var, "Listen") == 0) {
|
||||
if (Conf_ListenAddress) {
|
||||
Config_Error(LOG_ERR,
|
||||
|
@ -111,6 +111,9 @@ GLOBAL char Conf_ServerAdminMail[CLIENT_INFO_LEN];
|
||||
/** Message of the day (MOTD) of this server */
|
||||
GLOBAL array Conf_Motd;
|
||||
|
||||
/** Help text of this server */
|
||||
GLOBAL array Conf_Helptext;
|
||||
|
||||
/** Array of ports this server should listen on */
|
||||
GLOBAL array Conf_ListenPorts;
|
||||
|
||||
|
@ -77,6 +77,9 @@
|
||||
/** Name of the MOTD file. */
|
||||
#define MOTD_FILE "/ngircd.motd"
|
||||
|
||||
/** Name of the help file. */
|
||||
#define HELP_FILE "/Commands.txt"
|
||||
|
||||
/** Default chroot() directory. */
|
||||
#define CHROOT_DIR ""
|
||||
|
||||
|
108
src/ngircd/irc.c
108
src/ngircd/irc.c
@ -44,6 +44,7 @@ static bool Send_Message PARAMS((CLIENT *Client, REQUEST *Req, int ForceType,
|
||||
static bool Send_Message_Mask PARAMS((CLIENT *from, char *command,
|
||||
char *targetMask, char *message,
|
||||
bool SendErrors));
|
||||
static bool Help PARAMS((CLIENT *Client, const char *Topic));
|
||||
|
||||
|
||||
/**
|
||||
@ -315,29 +316,116 @@ IRC_TRACE( CLIENT *Client, REQUEST *Req )
|
||||
} /* IRC_TRACE */
|
||||
|
||||
|
||||
/**
|
||||
* Handler for the IRC "HELP" command.
|
||||
*
|
||||
* @param Client The client from which this command has been received.
|
||||
* @param Req Request structure with prefix and all parameters.
|
||||
* @return CONNECTED or DISCONNECTED.
|
||||
*/
|
||||
GLOBAL bool
|
||||
IRC_HELP( CLIENT *Client, REQUEST *Req )
|
||||
IRC_HELP(CLIENT *Client, REQUEST *Req)
|
||||
{
|
||||
COMMAND *cmd;
|
||||
|
||||
assert( Client != NULL );
|
||||
assert( Req != NULL );
|
||||
assert(Client != NULL);
|
||||
assert(Req != NULL);
|
||||
|
||||
/* Bad number of arguments? */
|
||||
if( Req->argc > 0 ) return IRC_WriteStrClient( Client, ERR_NORECIPIENT_MSG, Client_ID( Client ), Req->command );
|
||||
if (Req->argc > 1)
|
||||
return IRC_WriteStrClient(Client, ERR_NORECIPIENT_MSG,
|
||||
Client_ID(Client), Req->command);
|
||||
|
||||
cmd = Parse_GetCommandStruct( );
|
||||
while( cmd->name )
|
||||
{
|
||||
if( ! IRC_WriteStrClient( Client, "NOTICE %s :%s", Client_ID( Client ), cmd->name )) return DISCONNECTED;
|
||||
IRC_SetPenalty(Client, 2);
|
||||
|
||||
if ((Req->argc == 0 && array_bytes(&Conf_Helptext) > 0)
|
||||
|| (Req->argc >= 1 && strcasecmp(Req->argv[0], "Commands") != 0)) {
|
||||
/* Help text available and requested */
|
||||
if (Req->argc >= 1)
|
||||
return Help(Client, Req->argv[0]);
|
||||
|
||||
if (!Help(Client, "Intro"))
|
||||
return DISCONNECTED;
|
||||
return CONNECTED;
|
||||
}
|
||||
|
||||
cmd = Parse_GetCommandStruct();
|
||||
while(cmd->name) {
|
||||
if (!IRC_WriteStrClient(Client, "NOTICE %s :%s",
|
||||
Client_ID(Client), cmd->name))
|
||||
return DISCONNECTED;
|
||||
cmd++;
|
||||
}
|
||||
|
||||
IRC_SetPenalty( Client, 2 );
|
||||
return CONNECTED;
|
||||
} /* IRC_HELP */
|
||||
|
||||
|
||||
/**
|
||||
* Send help for a given topic to the client.
|
||||
*
|
||||
* @param Client The client requesting help.
|
||||
* @param Topoc The help topic requested.
|
||||
* @return CONNECTED or DISCONNECTED.
|
||||
*/
|
||||
static bool
|
||||
Help(CLIENT *Client, const char *Topic)
|
||||
{
|
||||
char *line;
|
||||
size_t helptext_len, len_str, idx_start, lines = 0;
|
||||
bool in_article = false;
|
||||
|
||||
assert(Client != NULL);
|
||||
assert(Topic != NULL);
|
||||
|
||||
helptext_len = array_bytes(&Conf_Helptext);
|
||||
line = array_start(&Conf_Helptext);
|
||||
while (helptext_len > 0) {
|
||||
len_str = strlen(line) + 1;
|
||||
assert(helptext_len >= len_str);
|
||||
helptext_len -= len_str;
|
||||
|
||||
if (in_article) {
|
||||
/* The first character in each article text line must
|
||||
* be a TAB (ASCII 9) character which will be stripped
|
||||
* in the output. If it is not a TAB, the end of the
|
||||
* article has been reached. */
|
||||
if (line[0] != '\t') {
|
||||
if (lines > 0)
|
||||
return CONNECTED;
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
/* A single '.' character indicates an empty line */
|
||||
if (line[1] == '.' && line[2] == '\0')
|
||||
idx_start = 2;
|
||||
else
|
||||
idx_start = 1;
|
||||
|
||||
if (!IRC_WriteStrClient(Client, "NOTICE %s :%s",
|
||||
Client_ID(Client),
|
||||
&line[idx_start]))
|
||||
return DISCONNECTED;
|
||||
lines++;
|
||||
|
||||
} else {
|
||||
if (line[0] == '-' && line[1] == ' '
|
||||
&& strcasecmp(&line[2], Topic) == 0)
|
||||
in_article = true;
|
||||
}
|
||||
|
||||
line += len_str;
|
||||
}
|
||||
|
||||
/* Help topic not found (or empty)! */
|
||||
if (!IRC_WriteStrClient(Client, "NOTICE %s :No help for \"%s\" found!",
|
||||
Client_ID(Client), Topic))
|
||||
return DISCONNECTED;
|
||||
|
||||
return CONNECTED;
|
||||
}
|
||||
|
||||
|
||||
static char *
|
||||
#ifdef ZLIB
|
||||
Option_String(CONN_ID Idx)
|
||||
|
Loading…
Reference in New Issue
Block a user