This repository has been archived on 2021-04-17. You can view files and clone it, but cannot push or open issues or pull requests.
uIRC/src/uirc.c

149 lines
4.0 KiB
C
Raw Normal View History

2020-06-22 16:58:10 +00:00
/*
* This file is part of uIRC. (https://git.redxen.eu/caskd/uIRC)
* Copyright (c) 2019, 2020 Alex-David Denes
*
* uIRC is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* uIRC is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with uIRC. If not, see <https://www.gnu.org/licenses/>.
*/
#include "uirc.h"
const char* uirc_ircmd[] = {
[PASS] = "PASS",
[NICK] = "NICK",
[USER] = "USER",
[SERVER] = "SERVER",
[OPER] = "OPER",
[QUIT] = "QUIT",
[SQUIT] = "SQUIT",
[JOIN] = "JOIN",
[PART] = "PART",
[MODE] = "MODE",
[TOPIC] = "TOPIC",
[NAMES] = "NAMES",
[LIST] = "LIST",
[INVITE] = "INVITE",
[KICK] = "KICK",
[VERSION] = "VERSION",
[STATS] = "STATS",
[LINKS] = "LINKS",
[TIME] = "TIME",
[CONNECT] = "CONNECT",
[TRACE] = "TRACE",
[ADMIN] = "ADMIN",
[INFO] = "INFO",
[PRIVMSG] = "PRIVMSG",
[NOTICE] = "NOTICE",
[WHO] = "WHO",
[WHOIS] = "WHOIS",
[WHOWAS] = "WHOWAS",
[KILL] = "KILL",
[PING] = "PING",
[PONG] = "PONG",
[ERROR] = "ERROR",
[AWAY] = "AWAY",
[REHASH] = "REHASH",
[RESTART] = "RESTART",
[SUMMON] = "SUMMON",
[USERS] = "USERS",
[WALLOPS] = "WALLOPS",
[USERHOST] = "USERHOST",
[ISON] = "ISON"};
int uirc_tokenize_message(struct irc_message* irc_msg, char* line)
{
char *progr, *command;
2020-06-22 16:59:23 +00:00
progr = line;
2020-06-22 16:58:10 +00:00
2020-06-22 16:59:23 +00:00
if (*progr == '@') {
char* tags;
if ((tags = strtok_r(progr + 1, " ", &progr)) != NULL) {
char *ctag = tags, *cval;
do {
if ((cval = strchr(ctag, '=')) != NULL) {
*(cval++) = '\0';
if (!strcmp(ctag, "time")) {
irc_msg->tags.time = cval;
} else if (!strcmp(ctag, "account")) {
irc_msg->tags.account = cval;
} else if (!strcmp(ctag, "batch")) {
irc_msg->tags.batch = cval;
} else if (!strcmp(ctag, "label")) {
irc_msg->tags.label = cval;
} else if (!strcmp(ctag, "msgid")) {
irc_msg->tags.msgid = cval;
} else if (!strcmp(ctag, "multiline-concat")) {
irc_msg->tags.multiline_concat = cval;
}
if ((ctag = strchr(cval, ';')) != NULL)
*(ctag++) = '\0';
}
} while (ctag != NULL);
} else
return 0;
}
2020-06-22 16:58:10 +00:00
if (*progr == ':') {
char* prefix;
2020-06-22 16:59:23 +00:00
if ((prefix = strtok_r(progr + 1, " ", &progr)) != NULL) {
2020-06-22 16:58:10 +00:00
if ((irc_msg->source.host = strchr(prefix, '@')) != NULL) {
*(irc_msg->source.host++) = '\0';
if ((irc_msg->source.user = strchr(prefix, '!')) != NULL)
*(irc_msg->source.user++) = '\0';
}
2020-06-22 16:59:23 +00:00
irc_msg->source.nick = prefix; /* NOTE: This may be the server instead of a nick according to RFC2812, it is left to the library user to decide how to interpret this based on the context. */
} else
return 0;
2020-06-22 16:58:10 +00:00
}
command = strtok_r(progr, " ", &progr);
if (isalpha(*command)) {
if (!(irc_msg->cmd = uirc_ircmd_stoi(command)))
return 0;
} else if (isdigit(*command)) {
if ((irc_msg->cmd = atoi(command)) == 0)
return 0;
} else {
return 0;
}
int i;
for (i = 0; *progr != ':' && i < 14; i++) {
if ((irc_msg->args[i] = strtok_r(NULL, " ", &progr)) == NULL)
return 0;
}
irc_msg->argc = i;
if (*progr == ':')
++progr;
irc_msg->msg = progr;
return 1;
}
unsigned int uirc_ircmd_stoi(char* str)
{
for (unsigned short i = PASS; i <= ISON; i++) {
if (strcmp(uirc_ircmd[i], str) == 0)
return i;
}
return 0;
}
int uirc_assm_mesg(char* buf, int comm, char* dest, char* msg)
{
if (buf == NULL)
return -2;
if (dest == NULL) {
if (sprintf(buf, "%s %s\r\n", uirc_ircmd[comm], msg) < 0)
return -1;
} else {
if (sprintf(buf, "%s %s %s\r\n", uirc_ircmd[comm], dest, msg) < 0)
return -1;
}
return 0;
}