diff options
| -rw-r--r-- | irc.c | 2 | ||||
| -rw-r--r-- | irc.h | 2 | ||||
| -rw-r--r-- | irc_commands.c | 28 | ||||
| -rw-r--r-- | irc_send.c | 7 | 
4 files changed, 38 insertions, 1 deletions
| @@ -726,7 +726,7 @@ void irc_desync(irc_t *irc)  int irc_check_login(irc_t *irc)  { -	if (irc->user->user && irc->user->nick) { +	if (irc->user->user && irc->user->nick && !(irc->status & USTATUS_CAP_PENDING)) {  		if (global.conf->authmode == AUTHMODE_CLOSED && !(irc->status & USTATUS_AUTHORIZED)) {  			irc_send_num(irc, 464, ":This server is password-protected.");  			return 0; @@ -48,6 +48,7 @@ typedef enum {  	USTATUS_IDENTIFIED = 4, /* To NickServ (root). */  	USTATUS_SHUTDOWN = 8,   /* Now used to indicate we're shutting down.  	                           Currently just blocks irc_vawrite(). */ +	USTATUS_CAP_PENDING = 16,  	/* Not really status stuff, but other kinds of flags: For slightly  	   better password security, since the only way to send passwords @@ -330,6 +331,7 @@ void irc_send_nick(irc_user_t *iu, const char *new_nick);  void irc_send_channel_user_mode_diff(irc_channel_t *ic, irc_user_t *iu,                                       irc_channel_user_flags_t old_flags, irc_channel_user_flags_t new_flags);  void irc_send_invite(irc_user_t *iu, irc_channel_t *ic); +void irc_send_cap(irc_t *irc, char *subcommand, char *body);  /* irc_user.c */  irc_user_t *irc_user_new(irc_t *irc, const char *nick); diff --git a/irc_commands.c b/irc_commands.c index 98579d99..078a59ff 100644 --- a/irc_commands.c +++ b/irc_commands.c @@ -28,6 +28,33 @@  #include "help.h"  #include "ipc.h" +static void irc_cmd_cap(irc_t *irc, char **cmd) +{ +	if (!(irc->status & USTATUS_LOGGED_IN)) { +		/* Put registration on hold until CAP END */ +		irc->status |= USTATUS_CAP_PENDING; +	} + +	if (g_strcasecmp(cmd[1], "LS") == 0) { +		/* gboolean irc302 = (g_strcmp0(cmd[2], "302") == 0); */ +		irc_send_cap(irc, "LS", ""); + +	} else if (g_strcasecmp(cmd[1], "LIST") == 0) { +		irc_send_cap(irc, "LIST", ""); + +	} else if (g_strcasecmp(cmd[1], "REQ") == 0) { +		irc_send_cap(irc, "NAK", cmd[2] ? : ""); + +	} else if (g_strcasecmp(cmd[1], "END") == 0) { +		irc->status &= ~USTATUS_CAP_PENDING; +		irc_check_login(irc); + +	} else { +		irc_send_num(irc, 410, "%s :Invalid CAP command", cmd[1]); +	} + +} +  static void irc_cmd_pass(irc_t *irc, char **cmd)  {  	if (irc->status & USTATUS_LOGGED_IN) { @@ -684,6 +711,7 @@ static void irc_cmd_rehash(irc_t *irc, char **cmd)  }  static const command_t irc_commands[] = { +	{ "cap",         1, irc_cmd_cap,         0 },  	{ "pass",        1, irc_cmd_pass,        0 },  	{ "user",        4, irc_cmd_user,        IRC_CMD_PRE_LOGIN },  	{ "nick",        1, irc_cmd_nick,        0 }, @@ -427,3 +427,10 @@ void irc_send_invite(irc_user_t *iu, irc_channel_t *ic)  	irc_write(iu->irc, ":%s!%s@%s INVITE %s :%s",  	          iu->nick, iu->user, iu->host, irc->user->nick, ic->name);  } + +void irc_send_cap(irc_t *irc, char *subcommand, char *body) +{ +	char *nick = irc->user->nick ? : "*"; + +	irc_write(irc, ":%s CAP %s %s :%s", irc->root->host, nick, subcommand, body); +} | 
