/***************************************************************************************/
/* Anope Module : bs_assign_limit.c : v1.1                                             */  
/* Trystan Scott Lee                                                                   */
/* trystan@nomadirc.net                                                                */ 
/*                                                                                     */
/* Anope (c) 2000-2005 Anope.org                                                       */
/*                                                                                     */ 
/* This program 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 1, or (at your option) any later version.                */
/*                                                                                     */
/*  This program 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.          */
/*                                                                                     */
/***************************************************************************************/

#include "module.h"

/***************************************************************************************/

#define MOD_NAME "bs_assign_limit"
#define MOD_AUTHOR "Trystan"
#define MOD_VERSION "1.1"

/***************************************************************************************/

#define BadPtr(x) (!(x) || (*(x) == '\0'))
#define ModFree(x) if (!BadPtr(x)) free(x)
#define YesNo(x) (x ? "On" : "Off")
int BSLimitEnabled;
int BSMaxAssign;
int do_assign(User * u);
int do_set(User * u);
int do_reload(int argc, char **argv);
int load_config(void);

#define LANG_NUM_STRINGS       3
#define BS_ASSIGN_LIMIT        0
#define BS_ASSIGN_LIMIT_SYNTAX 1
#define BS_ASSIGN_LIMIT_OFF    2
#define BS_ASSIGN_LIMIT_ON     3


/***************************************************************************************/

int AnopeInit(int argc, char **argv)
{
    Command *c;
    EvtHook *hook;
	int status;

    moduleAddAuthor(MOD_NAME);
    moduleAddVersion(MOD_VERSION);
    moduleSetType(THIRD);

    c = createCommand("ASSIGN", do_assign, NULL, -1, -1, -1, -1, -1);
    status = moduleAddCommand(BOTSERV, c, MOD_HEAD);
    if (status != MOD_ERR_OK) {
        /* something went wrong say something about */
        alog("[%s%s] unable to add handler for ASSIGN error [%d]", MOD_NAME, MODULE_EXT, status);
        return MOD_STOP;
    }

    c = createCommand("SET", do_set, NULL, -1, -1, -1, -1, -1);
    status = moduleAddCommand(BOTSERV, c, MOD_HEAD);
    if (status != MOD_ERR_OK) {
        /* something went wrong say something about */
        alog("[%s%s] unable to add handler for SET error [%d]", MOD_NAME, MODULE_EXT, status);
        return MOD_STOP;
    }

    hook = createEventHook(EVENT_RELOAD, do_reload);
    status = moduleAddEventHook(hook);
    if (status != MOD_ERR_OK) {
        /* something went wrong say something about */
        alog("[%s%s] unable to add handler for EVENT_RELOAD error [%d]", MOD_NAME, MODULE_EXT, status);
        return MOD_STOP;
    }

    if (!load_config()) {
        return MOD_STOP;
    }
    alog("[%s%s] successfully loaded", MOD_NAME, MODULE_EXT);
    return MOD_CONT;
}

/***************************************************************************************/

void AnopeFini(void)
{
    alog("Unloading %s", MOD_NAME);
}

/***************************************************************************************/

int do_reload(int argc, char **argv)
{
    load_config();
    return MOD_CONT;
}

/***************************************************************************************/

int do_set(User * u)
{
    char *buffer = moduleGetLastBuffer();
    char *option = myStrGetToken(buffer, ' ', 0); 
    char *value = myStrGetToken(buffer, ' ', 1);
    int is_servadmin = is_services_admin(u);

    if (readonly) {
		ModFree(option);
		ModFree(value);
        return MOD_CONT;
    } else if (BadPtr(option) || BadPtr(value)) {
        return MOD_CONT;
    } else if (is_servadmin && !stricmp(option, "LIMIT")) {
            if (!stricmp(value, "ON")) {
                BSLimitEnabled = 1;
				moduleNoticeLang(s_BotServ, u, BS_ASSIGN_LIMIT_ON, s_BotServ);
            } else if (!stricmp(value, "OFF")) {
                BSLimitEnabled = 0;
				moduleNoticeLang(s_BotServ, u, BS_ASSIGN_LIMIT_OFF, s_BotServ);
            } else {
				moduleNoticeLang(s_BotServ, u, BS_ASSIGN_LIMIT_SYNTAX);
            }
		ModFree(option);
		ModFree(value);
        return MOD_STOP;
    } else {
		ModFree(option);
		ModFree(value);
        return MOD_CONT;
    }
}

/***************************************************************************************/

int do_assign(User * u)
{
    char *buffer = moduleGetLastBuffer();
    char *chan;
    char *nick;
    BotInfo *bi;
    int countcheck;

    chan = myStrGetToken(buffer, ' ', 0);
    nick = myStrGetToken(buffer, ' ', 1);    

    if (BadPtr(chan) || BadPtr(nick)) {
        return MOD_CONT;
	} else if (readonly) {
   	    ModFree(chan);
	    ModFree(nick);
        return MOD_CONT;
    } else if (!(bi = findbot(nick))) {
   	    ModFree(chan);
	    ModFree(nick);
        return MOD_CONT;
    } else {
       countcheck = bi->chancount + 1;
       if (BSLimitEnabled && countcheck > BSMaxAssign) {
		   moduleNoticeLang(s_BotServ, u, BS_ASSIGN_LIMIT);
	  	   ModFree(chan);
		   ModFree(nick);
           return MOD_STOP;
       }
  	   ModFree(chan);
	   ModFree(nick);
       return MOD_CONT;
    }
}

/***************************************************************************************/

int load_config(void)
{
	int i;
	
    Directive confvalues[][1] = {
		{{"BSMaxAssign", {{PARAM_INT, PARAM_RELOAD, &BSMaxAssign}}}},
		{{"BSLimitEnabled", {{PARAM_SET, PARAM_RELOAD, &BSLimitEnabled}}}}
    };

	for (i = 0; i < 2; i++)
    	moduleGetConfigDirective(confvalues[i]);

    if (BSMaxAssign) {
        if (debug) {
            alog("debug: [%s] Set config vars: BSMaxAssign=%d BSLimitEnabled=%s", MOD_NAME, BSMaxAssign, YesNo(BSLimitEnabled));
        }
        return 1;
    } else {
        alog("[%s] BSMaxAssign NOT Set, please set BSMaxAssign in the services.conf", MOD_NAME);
        return 0;
    }
}

/***************************************************************************************/

void mAddLanguages(void)
{
    char *langtable_en_us[] = {
        /* BS_ASSIGN_LIMIT */
        "Channel assignment max has been reached can not assign bot",
		/* BS_ASSING_LIMIT_SYNTAX */
		"Syntax: SET LIMIT [on|off]",
		/* BS_ASSIGN_LIMIT_OFF */
		"%s Assign Limit disabled",
		/* BS_ASSIGN_LIMIT_ON */
		"%s Assign Limit enabled",
    };

    /* insert the english lang */
    moduleInsertLanguage(LANG_EN_US, LANG_NUM_STRINGS, langtable_en_us);
}



