Ejemplo n.º 1
0
Archivo: irc.c Proyecto: mintux/aqu4bot
void IRC_Loop(void)
{ /*Most of the action is triggered here.*/
	char MessageBuf[2048];
	
	while (1)
	{
		if (!Net_Read(SocketDescriptor, MessageBuf, sizeof MessageBuf, true))
		{ /*No command should ever call Net_Read() besides us and the connecting stuff that comes before us.*/
			puts("\033[31mCONNECTION LOST\033[0m");
			close(SocketDescriptor);
			exit(1);
		}
		
		if (!strncmp(MessageBuf, "PING ", strlen("PING "))) IRC_Pong(MessageBuf); /*Respond to pings.*/
		
		switch (IRC_GetMessageType(MessageBuf))
		{
			char Nick[1024], Ident[1024], Mask[1024];

			case IMSG_PRIVMSG:
			{
				char MessageData[2048], *TC = NULL, Channel[1024];
				unsigned long Inc = 0;
								
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;
				IRC_GetMessageData(MessageBuf, MessageData);
				
				if (Auth_IsBlacklisted(Nick, Ident, Mask)) continue; /*Says "you are not going to be listened to bud.*/
				
				if (strcmp(Nick, ServerInfo.Nick) != 0) Log_WriteMsg(MessageBuf, IMSG_PRIVMSG);
				
				for (; MessageData[Inc] != ' ' && MessageData[Inc] && Inc < sizeof Channel - 1; ++Inc)
				{
					Channel[Inc] = MessageData[Inc];
				}
				Channel[Inc] = '\0';
				
				TC = strchr(MessageData, ' ') + 1;
				
				if (*TC == ':') ++TC;
				
				if (*TC == 0x01)
				{ /*IRC escape code thingy...*/
					
					if (!strcmp(TC, "\01VERSION\01"))
					{
						IRC_Notice(Nick, "\01VERSION aqu4bot " BOT_VERSION "\01");
					}
					else if (!strncmp(TC, "\01PING", strlen("\01PING")))
					{
						IRC_Notice(Nick, TC);
					}
				}
				else
				{
					/*I don't feel like including time.h*/
					time_t time(time_t*);
										
					CMD_ProcessCommand(MessageBuf);
					
					if (strcmp(Nick, ServerInfo.Nick) != 0)
					{
						CMD_UpdateSeenDB(time(NULL), Nick, Channel, TC);
					}
				}
				break;
			}
			case IMSG_NOTICE:
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;
				
				if (Auth_IsBlacklisted(Nick, Ident, Mask)) continue;
				
				if (strcmp(Nick, ServerInfo.Nick) != 0) Log_WriteMsg(MessageBuf, IMSG_NOTICE);
				
				break;				
			case IMSG_INVITE:
			{
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;
				
				if (Auth_IsBlacklisted(Nick, Ident, Mask)) continue;
				
				if (Auth_IsAdmin(Nick, Ident, Mask, NULL))
				{
					const char *TWorker = MessageBuf;
					TWorker = strchr(TWorker, '#');
					
					if (!TWorker)
					{
						IRC_Message(Nick, "There is something wrong, and although you are an admin,"
									"your invite request is either malformed or it's my fault.");
						break;
					}
					
					IRC_Message(Nick, "Coming.");
					
					if (IRC_JoinChannel(TWorker)) IRC_AddChannelToTree(TWorker);
				}
				else
				{
					IRC_Message(Nick, "I'm sorry, I can only accept invite requests from my admins.");
				}
				break;
			}
			case IMSG_KICK:
			{
				char InBuf[2048], *Worker = InBuf;
				
				IRC_GetMessageData(MessageBuf, InBuf);
				
				Log_WriteMsg(MessageBuf, IMSG_KICK);
				
				if (!(Worker = strchr(InBuf, ' '))) break;
				
				*Worker = '\0';
				
				IRC_DelChannelFromTree(*InBuf == ':' ? InBuf + 1 : InBuf);
				break;
			}
			case IMSG_QUIT:
			{				
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;
				
				if (!strcmp(Nick, ServerInfo.Nick))
				{
					IRC_Quit(NULL);
					IRC_ShutdownChannelTree();
					Auth_ShutdownAdmin();
					CMD_SaveSeenDB();
					Auth_ShutdownBlacklist();
					exit(0);
				}
				break;
			}
			case IMSG_JOIN:
			{
				
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;
				
				Log_WriteMsg(MessageBuf, IMSG_JOIN);
				while (CMD_ReadTellDB(Nick));
				break;
			}
			case IMSG_PART:
				if (!IRC_BreakdownNick(MessageBuf, Nick, Ident, Mask)) continue;

				Log_WriteMsg(MessageBuf, IMSG_PART);
				break;
			case IMSG_NICK:
			{
				char NewNick[1024];

				IRC_GetMessageData(MessageBuf, NewNick);
				
				while (CMD_ReadTellDB(*NewNick == ':' ? NewNick + 1 : NewNick));
			}
			default:
				break;
		}
	}
}
Ejemplo n.º 2
0
bool Log_WriteMsg(const char *InStream, MessageType MType)
{
	char OutBuf[2048], Origin[2048], Message[2048];
	char Nick[128], Ident[128], Mask[128], *Worker = Origin;
	
	if (MType == IMSG_TOPIC) return Log_TopicLog(InStream);
	else if (MType == IMSG_MODE) return Log_ModeLog(InStream);
	
	if (!IRC_BreakdownNick(InStream, Nick, Ident, Mask) || !*Nick || !*Ident || !*Mask) return true;
		
	IRC_GetMessageData(InStream, Origin);
	
	
	if (MType != IMSG_JOIN && MType != IMSG_QUIT && MType != IMSG_NICK && MType != IMSG_PART)
	{
		Worker = strchr(Worker, ' ');
		*Worker++ = '\0';
		
		while (*Worker == ' ' ) ++Worker;
		
		if (*Worker == ':') ++Worker;
		
		strncpy(Message, Worker, sizeof Message - 1);
		Message[sizeof Message - 1] = '\0';
	}
	
	if (MType == IMSG_PART || MType == IMSG_JOIN) /*I really doubt I'll ever see that on a JOIN.*/
	{
		if ((Worker = strstr(Origin, " :"))) *Worker = '\0';
	}
	else if (MType == IMSG_KICK)
	{
		if ((Worker = strstr(Message, " :"))) *Worker = '\0';
	}

	switch (MType)
	{		
		case IMSG_PRIVMSG:
			if (!strncmp(Message, "\01ACTION", strlen("\01ACTION")))
			{
				char *Temp =  strchr(Message + 1, '\01');
				
				if (Temp) *Temp = '\0';
				
				snprintf(OutBuf, sizeof OutBuf, "(%s) **%s %s**",
						*Origin == '#' ? Origin : Nick, Nick, Message + strlen("\01ACTION "));
			}
			else snprintf(OutBuf, sizeof OutBuf, "(%s) <%s>: %s", *Origin == '#' ? Origin : Nick, Nick, Message);
			break;
		case IMSG_NOTICE:
			snprintf(OutBuf, sizeof OutBuf, "(%s) <%s> (notice): %s", *Origin == '#' ? Origin : Nick, Nick, Message);
			break;
		case IMSG_JOIN:
			snprintf(OutBuf, sizeof OutBuf, "<%s!%s@%s joined %s>", Nick, Ident, Mask, Origin);
			break;
		case IMSG_PART:
			snprintf(OutBuf, sizeof OutBuf, "<%s!%s@%s left %s>", Nick, Ident, Mask, Origin);
			break;
		case IMSG_KICK:
			snprintf(OutBuf, sizeof OutBuf, "<%s was kicked from %s by %s>", Message, Origin, Nick);
			break;
		case IMSG_NICK:
		case IMSG_QUIT:
		{
			struct ChannelTree *Worker = Channels;
			
			if (MType == IMSG_QUIT)
			{
				snprintf(OutBuf, sizeof OutBuf, "<%s!%s@%s has quit: %s>", Nick, Ident, Mask, *Origin == ':' ? Origin + 1 : Origin);
			}
			else
			{
				snprintf(OutBuf, sizeof OutBuf, "<%s is now known as %s>", Nick, Origin);
			}
			
			if (!Channels)
			{
				Log_CoreWrite(OutBuf, Nick);
				return true;
			}
			
			for (; Worker; Worker = Worker->Next)
			{
				if (IRC_UserInChannelP(Worker, Nick))
				{
					Log_CoreWrite(OutBuf, Worker->Channel);
					NoLogToConsole = true;
				}
			}
			
			NoLogToConsole = false;
			return true;
		}
		default:
			return false;
	}

	Log_CoreWrite(OutBuf, *Origin == '#' ? Origin : Nick);
	
	return true;
}
Ejemplo n.º 3
0
Bool Log_WriteMsg(const char *InStream, MessageType MType)
{
	FILE *Descriptor = NULL;
	char Filename[1024], OutBuf[2048], Origin[2048], Message[2048];
	char Nick[1024], Ident[1024], Mask[1024], *Worker = Origin;
	time_t Time = time(NULL);
	struct tm TimeStruct;
	char TimeString[1024];
	struct stat DirStat;
	
	if (!Logging) return true;
	
	if (!IRC_BreakdownNick(InStream, Nick, Ident, Mask) || !*Nick || !*Ident || !*Mask) return true;
		
	IRC_GetMessageData(InStream, Origin);
	
	if (*Origin != '#' && !LogPMs) return true;
	
	if (MType != IMSG_JOIN && MType != IMSG_PART)
	{
		Worker = strchr(Worker, ' ');
		*Worker++ = '\0';
		
		while (*Worker == ' ' ) ++Worker;
		
		if (*Worker == ':') ++Worker;
		
		strncpy(Message, Worker, sizeof Message - 1);
		Message[sizeof Message - 1] = '\0';
	}
	
	if (MType == IMSG_PART || MType == IMSG_JOIN) /*I really doubt I'll ever see that on a JOIN.*/
	{
		if ((Worker = strstr(Origin, " :"))) *Worker = '\0';
	}
	else if (MType == IMSG_KICK)
	{
		if ((Worker = strstr(Message, " :"))) *Worker = '\0';
	}
	
	if (stat("logs", &DirStat) != 0)
	{
		if (mkdir("logs", 0755) != 0) return false;
	}
	
	snprintf(Filename, sizeof Filename, "logs/%s.txt", *Origin == '#' ? Origin : Nick);
	
	gmtime_r(&Time, &TimeStruct);
	strftime(TimeString, sizeof TimeString, "[%Y-%m-%d %H:%M:%S UTC]", &TimeStruct);

	switch (MType)
	{		
		case IMSG_PRIVMSG:
			if (!strncmp(Message, "\01ACTION", strlen("\01ACTION")))
			{
				char *Temp =  strchr(Message + 1, '\01');
				
				if (Temp) *Temp = '\0';
				
				snprintf(OutBuf, sizeof OutBuf, "%s **%s %s**\n", TimeString, Nick, Message + strlen("\01ACTION "));
			}
			else snprintf(OutBuf, sizeof OutBuf, "%s %s: %s\n", TimeString, Nick, Message);
			break;
		case IMSG_NOTICE:
			snprintf(OutBuf, sizeof OutBuf, "%s %s (notice): %s\n", TimeString, Nick, Message);
			break;
		case IMSG_JOIN:
			snprintf(OutBuf, sizeof OutBuf, "%s <%s joined %s>\n", TimeString, Nick, Origin);
			break;
		case IMSG_PART:
			snprintf(OutBuf, sizeof OutBuf, "%s <%s left %s>\n", TimeString, Nick, Origin);
			break;
		case IMSG_KICK:
			snprintf(OutBuf, sizeof OutBuf, "%s <%s was kicked from %s by %s>\n", TimeString, Message, Origin, Nick);
			break;
		default:
			return false;
	}
	
	if (!(Descriptor = fopen(Filename, "a")))
	{
		return false;
	}
	
	fwrite(OutBuf, 1, strlen(OutBuf), Descriptor);
	fclose(Descriptor);
	
	return true;
}