irctk

libircclient binding for scripts
git clone https://a3nm.net/git/irctk/
Log | Files | Refs | README

commit 62a9c2a2f23538d354c2cc426d552ec136bdf201
parent c9c41ba4192e36e8abae8c4a136fbd3d43456201
Author: Antoine Amarilli <a3nm@a3nm.net>
Date:   Sun,  1 Jul 2012 21:28:14 +0200

Merge branch 'for-autonomic' of git://gitorious.org/~elarnon/irctk/elarnons-irctk into merge

Conflicts:
	irctk.c

Diffstat:
irctk.c | 95+++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------------------
1 file changed, 69 insertions(+), 26 deletions(-)

diff --git a/irctk.c b/irctk.c @@ -1050,6 +1050,38 @@ const char *output_nick(const char *nick) { return result; } +#define MATCH_CMD(str, cmd) \ + ( strncmp((str) + 1, (cmd " "), sizeof(cmd) / sizeof(char) ) \ + ? NULL : (str) + sizeof(cmd) / sizeof(char) + 1 ) + +#define MATCH_CMD0(str, cmd) \ + ( strncmp((str) + 1, (cmd), sizeof(cmd) / sizeof(char) - 1) \ + ? NULL : (str) + sizeof(cmd) / sizeof(char) ) + +#define IS_END(ptr) ( !(ptr) || (ptr) == '\n' ) + +/* return value should be freed by callee */ +char* consume_word(char **from) +{ + const char *start; + char *result; + int size = 0; + while (**from == ' ') + ++*from; + start = *from; + while (**from != ' ' && !IS_END(**from)) { + ++*from; + ++size; + } + while (**from == ' ') + ++*from; + result = malloc((size + 1) * sizeof(char)); + assert(result); + strncpy(result, start, size); + result[size] = 0; + return result; +} + /* Send a message or do a command */ int do_cmd_msg(irc_session_t *s, char* chan, char* line) { @@ -1062,48 +1094,58 @@ int do_cmd_msg(irc_session_t *s, char* chan, char* line) /* TODO2 find a way to get real host name (part after !) */ /* TODO2 only join channels we haven't joined yet */ - join_channel (s, chan); - + join_channel(s, chan); /* TODO2 provide a means to escape '/' */ if (line[0] == '/' && args.command_to_event) { - if (strstr(line + 1, "nick ") == line + 1 ) + char *arg; + if ((arg = MATCH_CMD(line, "nick"))) { - is_local = 0; - rsl = irc_cmd_nick (s, line+6); - } else if (strstr(line + 1, "part") == line + 1) { - if (!line[5] || line[5] == '\n') + rsl = irc_cmd_nick (s, arg); + } else if ((arg = MATCH_CMD0(line, "part"))) { + if (!*arg || *arg == '\n') { rsl = irc_cmd_part(s, chan); - } else if (line[5] == ' ') { - rsl = irc_cmd_part(s, line + 6); + } else if (*arg == ' ') { + rsl = irc_cmd_part(s, arg); } - } else if (strstr(line + 1, "join") == line + 1) { - if (!line[5] || line[5] == '\n') + } else if ((arg = MATCH_CMD0(line, "join"))) { + if (!*arg || *arg == '\n') { debug("join %s", chan); rsl = join_channel(s, chan); - } else if (line[5] == ' ') { - debug("join %s", line+6); - rsl = join_channel(s, line + 6); + } else if (*arg == ' ') { + debug("join %s", arg); + rsl = join_channel(s, arg); } - } else if (strstr(line + 1, "topic ") == line + 1) { - debug("topic %s", line+6); - rsl = irc_cmd_topic(s, chan, line + 6); - } else if (strstr(line + 1, "quit") == line + 1) { - /* TODO notify main thread that it is over */ - is_local = 0; - if (!line[5] || line[5] == '\n') - { + } else if ((arg = MATCH_CMD(line, "topic"))) { + debug("topic %s", arg); + rsl = irc_cmd_topic(s, chan, arg); + } else if ((arg = MATCH_CMD0(line, "quit"))) { + // TODO notify main thread that is is over + if (IS_END(*arg)) { rsl = irc_cmd_quit(s, NULL); - } else if (line[5] == ' ') { - rsl = irc_cmd_quit(s, line + 6); + } else if (*arg == ' ') { + rsl = irc_cmd_quit(s, arg); + } + } else if ((arg = MATCH_CMD(line, "invite"))) { + char *inick = consume_word(&arg); + if (!IS_END(*arg)) { + rsl = irc_cmd_invite(s, inick, arg); } + free(inick); + } else if ((arg = MATCH_CMD(line, "kick"))) { + char *knick = consume_word(&arg); + rsl = irc_cmd_kick(s, knick, chan, arg); + free(knick); + } else if ((arg = MATCH_CMD0(line, "say"))) { + // just a way to escape messages starting by '/' + rsl = irc_cmd_msg(s, chan, arg); } else if (line[1] == ' ') { - // escaped message "/ /message" + // another way, compatible with irssi: "/ /message" rsl = irc_cmd_msg (s, chan, line + 2); } - // TODO: invite, names, list, topic, chanmode, kick, usermode, whois, raw... + // TODO: names, list, topic, chanmode, usermode, whois, raw... // with correct user tracking! } else { if (args.track != NO) { @@ -1247,6 +1289,7 @@ void cmd_msg(char *full_line, char *target, char *line) } void saw_user(const char *nick) { + if (!nick) return; if (!surface_nick_exists(&fifos, nick)) { // unknown user, register him debug("Register this new user");