/* * irccommands.c * (C) Peter Salanki 2002 * This program is copyright, and covered by the Gnu Public License. * The Natasha bot. * sorcer@linux.se */ #include #include #include #include #include #include #include #include #include #include #include "globals.h" #include "bottypes.h" void settopic (char *channel, char *topic) { char msg[512]; snprintf(msg, 512, "TOPIC %s :%s\n\r", channel, topic); putserver(msg, findchannel(channel)->arm); } void op (char *channel, char *nick) { char msg[512]; printf("Chan: %s Nick:%s\n", channel, nick); snprintf(msg, 512, "MODE %s +o %s\n\r", channel, nick); #ifdef MAIN if(strcmp(HOMECHAN, channel) != 0) putserver (msg, findchannel(channel)->arm); else putserver (msg, firstarm); #else putserver (msg, findchannel(channel)->arm); #endif } void deop (char *channel, char *nick) { char msg[512]; snprintf(msg, 512, "MODE %s -o %s\n\r", channel, nick); putserver (msg, findchannel(channel)->arm); } void voice (char *channel, char *nick) { char msg[512]; snprintf(msg, 512, "MODE %s +v %s\n\r", channel, nick); #ifdef MAIN if(strcmp(HOMECHAN, channel) != 0) putserver (msg, findchannel(channel)->arm); else putserver (msg, firstarm); #else putserver (msg, findchannel(channel)->arm); #endif } void devoice (char *channel, char *nick) { char msg[512]; snprintf(msg, 512, "MODE %s -v %s\n\r", channel, nick); putserver (msg, findchannel(channel)->arm); } void invite (struct channel *c, char *nick) { char msg[512]; snprintf(msg, 512, "INVITE %s %s\n\r", nick, c->name); putserver (msg, c->arm); } void kick (char *channel, char *nick, char reason[]) { char msg[512]; snprintf(msg, 512, "KICK %s %s :%s\n\r", channel, nick, reason); #ifdef MAIN if(strcmp(HOMECHAN, channel) != 0) putserver (msg, findchannel(channel)->arm); else putserver (msg, firstarm); #else putserver (msg, findchannel(channel)->arm); #endif } void nick (char *nick, struct arm *a) { char msg[512]; snprintf(msg, 512, "NICK %s\n\r", nick); putserver (msg, a); } void joinchannel (struct channel *c) { char query[512]; snprintf(query, 512, "JOIN %s %s\n\r", c->name, c->key); putserver (query, c->arm); c->ison = 0; // Assume we are NOT on the channel ++c->arm->channels; sprintf(query, "UPDATE `arms` SET `channels` = '%i' WHERE `id` = '%i'", c->arm->channels, c->arm->id); dbquery(query); EndDbQuery(); } void rejoinchannel (char channame[CHANNELLEN], struct arm *a) { struct channel *c; char msg[512]; c = findchannel(channame); snprintf(msg, 512, "JOIN %s", channame); if(c != NULL && strcmp(c->key, "") != 0) { strcat(msg, " "); strcat(msg, c->key); } #ifdef SAFEHOME else if (c == NULL) { strcat(msg," "); strcat(msg, homekey); } #endif strcat(msg, "\n\r"); putserver(msg, a); if(c != NULL) c->ison = 0; // Assume we are NOT on the channel } void who (struct channel *c) { /* Make a WHO and add all users. */ char who[CHANNELLEN+40]; sprintf(who, "WHO %s %%uhfcnua\n\r", c->name); putserver (who, c->arm); c->isop = 2; // Assume we have ops } void cyclechannel (struct channel *c, char *reason) { /* Function to cycle a channel */ char msg[512]; /* First we part */ sprintf(msg, "PART %s :%s\n\r", c->name, reason); putserver (msg, c->arm); OutOfChannel(c); /* Delete activechanusers and stuff */ /* Then we rejoin */ rejoinchannel (c->name, c->arm); } void partchannel (struct channel *c, char reason[]) { char msg[512]; char query[512]; sprintf(msg, "PART %s :%s\n\r", c->name, reason); putserver (msg, c->arm); sprintf(query, "UPDATE `arms` SET `channels` = '%i' WHERE `id` = '%i'", c->arm->channels, c->arm->id); dbquery(query); EndDbQuery(); } void sayf(char *victim, struct arm *a, struct activeuser *u, char *fmt, ...) { int n, size = 100; char *p; va_list ap; if ((p = Malloc(size)) == NULL) { printf("Debug: Malloc() Failed (query)\n"); return; } while (1) { /* Try to print in the allocated space. */ va_start(ap, fmt); n = vsnprintf (p, size, fmt, ap); va_end(ap); if (n > -1 && n < size) { say(victim, p, a, u); Free(p); return; } /* Else try again with more space. */ size = n+1; /* precisely what is needed */ if ((p = Realloc(p, size)) == NULL) { printf("Debug: Realloc() Failed (query)\n"); return; } } } void say (char *victim, char *words, struct arm *a, struct activeuser *u) { char msg[512]; #ifdef CNOTICE struct aculink *aculink; if(u != NULL) { aculink = u->firstlink; while (aculink != NULL) { if(aculink->link->channel->isop == 1 && aculink->link->channel->arm == a) { snprintf(msg, 512, "CNOTICE %s %s :%s\n\r", victim, aculink->link->channel->name, words); putserver(msg, aculink->link->channel->arm); return; } aculink = aculink->next; } } #endif // No optimal CNOTICE possible, use normal notice sprintf(msg, "NOTICE %s :%s\n\r", victim, words); putserver(msg, a); // The arm } void bestsay (char *victim, char *words) { char msg[512]; snprintf(msg, 512, "NOTICE %s :%s\n\r", victim, words); if(victim[0] == '#') putserver(msg, findchannel(victim)->arm); // The bot which is on that channel else putserver(msg, bestarm()); // The best arm } #ifdef CNOTICE void cnotice (char *victim, char *words) { char msg[512]; struct aculink *aculink; struct activeuser *u; u = findauser(victim); if(u != NULL) { aculink = u->firstlink; while (aculink != NULL) { if(aculink->link->channel->isop == 1) { snprintf(msg, 512, "CNOTICE %s %s :%s\n\r", victim, aculink->link->channel->name, words); putserver(msg, aculink->link->channel->arm); return; } aculink = aculink->next; } } // No CNOTICE possible, use normal notice bestsay(victim, words); // The fest arm } #endif void serverpong(char data[], struct arm *a) { int i, u; char ping[100], msg[512]; i = u =0; while (data[i] != ':') ++i; ++i; while ((ping[u] = data[i]) != '\0') { ++i; ++u; } snprintf(msg, 512, "PONG :%s\n\r", ping); puttoserver(msg, a); } void privmsgf(char *victim, char *fmt, ...) { int n, size = 100; char *p; va_list ap; if ((p = Malloc(size)) == NULL) { printf("Debug: Malloc() Failed (query)\n"); return; } while (1) { /* Try to print in the allocated space. */ va_start(ap, fmt); n = vsnprintf (p, size, fmt, ap); va_end(ap); if (n > -1 && n < size) { privmsg(victim, p); Free(p); return; } /* Else try again with more space. */ size = n+1; /* precisely what is needed */ if ((p = Realloc(p, size)) == NULL) { printf("Debug: Realloc() Failed (query)\n"); return; } } } void privmsg (char *victim, char *words) { char msg[512]; snprintf(msg, 512, "PRIVMSG %s :%s\n\r", victim, words); if(victim[0] == '#') { if(strcasecmp(victim, HOMECHAN) == 0) putserver(msg, bestarm()); else putserver(msg, findchannel(victim)->arm); } else putserver(msg, bestarm()); } void exprivmsg (char *victim, char *words, struct arm *a) { char msg[512]; snprintf(msg, 512, "PRIVMSG %s :%s\n\r", victim, words); putserver(msg, a); } #ifdef L void l_getop(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "OP %s", c->name); exprivmsg(L_NICK, msg, c->arm); } void l_invite(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "INVITE %s", c->name); exprivmsg(L_NICK, msg, c->arm); } void l_clearbans(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "unbanall %s", c->name); exprivmsg(L_NICK, msg, c->arm); } void l_whoami(struct arm *a) { exprivmsg(L_NICK, "WHOAMI", a); } #endif #ifdef Q void q_auth(struct arm *a) { char msg[512]; snprintf(msg, 512, "AUTH %s " Q_PASS, a->auth); exprivmsg(Q_NICK "@" Q_HOST, msg, a); #ifdef DEBUG printf("Q AUTH'd (%s).\n", a->nick); #endif } void q_getop(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "OP %s", c->name); exprivmsg(Q_NICK, msg, c->arm); } void q_invite(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "INVITE %s", c->name); exprivmsg(Q_NICK, msg, c->arm); } void q_clearbans(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "unbanall %s", c->name); exprivmsg(Q_NICK, msg, c->arm); } void o_requestop(struct channel *c) { char msg[256+CHANNELLEN]; snprintf(msg, 256+CHANNELLEN, "REQUESTOP %s", c->name); exprivmsg("O", msg, c->arm); } #endif void act (struct channel *c, char *words) { char buffer[512]; snprintf(buffer, 512, "ACTION %s", words); ctcp (c->name, buffer, c->arm); } void ctcp (char *victim, char *what, struct arm *a) { char msg[512]; snprintf(msg, 512, "PRIVMSG %s :\01%s\01\n\r", victim, what); putserver (msg, a); } void ctcpreply (char *victim, char *what, struct arm *a) { char msg[512]; snprintf(msg, 512, "NOTICE %s :\01%s\01\n\r", victim, what); putserver (msg, a); } void pong (struct arm *a) { char msg[50]; char buffer[32]; sprintf (buffer, " %ld ", (long) time (0)); sprintf(msg, "PONG :%s\n\r", buffer); putserver(msg, a); } void dumpmessage (char *victim, char *message) { char buffer[512]; int i, j; i = 0; j = 0; while (i < strlen (message)) { j = 0; while ((message[i] != '\n') && (j < 512) && (message[i])) { buffer[j] = message[i]; j++; i++; } buffer[j] = 0; bestsay(victim, buffer); i++; } }