From d56572bf926365f4e7c901aafd9a138ba9c92aab Mon Sep 17 00:00:00 2001 From: pk910 Date: Thu, 1 Sep 2011 04:31:14 +0200 Subject: [PATCH] continued cmd_neonserv_set.c --- bot_NeonServ.c | 9 ++ cmd_neonserv_set.c | 284 ++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 276 insertions(+), 17 deletions(-) diff --git a/bot_NeonServ.c b/bot_NeonServ.c index dd8a0eb..dff7184 100644 --- a/bot_NeonServ.c +++ b/bot_NeonServ.c @@ -107,6 +107,15 @@ static const struct default_language_entry msgtab[] = { {"NS_SET_HEADER", "Channel Settings for %s:"}, {"NS_SET_ON", "on"}, {"NS_SET_OFF", "off"}, + {"NS_SET_UNKNOWN_SETTING", "\002%s\002 is an unknown channel setting."}, + {"NS_SET_CANNOT_SET", "That setting is above your current level, so you cannot change it."}, + {"NS_SET_BADLEVEL", "You cannot change any setting to above your level."}, + {"NS_SET_INVALID_OPTION", "\002%d\002 is not a valid choice. Choose one:"}, + {"NS_SET_INVALID_BOOLEAN", "\002%s\002 is an invalid binary value."}, + {"NS_SET_DEFAULTS_OWNER", "You must have access 500 in %s to reset it to the default options."}, + {"NS_SET_DEFAULTS_CODE", "To reset %s's settings to the defaults, you must use 'set defaults %s'."}, + {"NS_SET_DEFAULTS_DONE", "All settings for %s have been reset to default values."}, + {"NS_SET_TRIGGER_OWNER", "You must have access 500 in %s to change the channel trigger."}, {NULL, NULL} }; diff --git a/cmd_neonserv_set.c b/cmd_neonserv_set.c index 353287a..2ab296f 100644 --- a/cmd_neonserv_set.c +++ b/cmd_neonserv_set.c @@ -1,9 +1,10 @@ -typedef char* neonserv_cmd_set_function(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument); -static char* neonserv_cmd_set_trigger(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument); -static char* neonserv_cmd_set_modes(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument); -static char* neonserv_cmd_set_dynlimit(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument); -static char* neonserv_cmd_set_nodelete(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument); +typedef char* neonserv_cmd_set_function(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); +static char* neonserv_cmd_set_setting(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); +static char* neonserv_cmd_set_trigger(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); +static char* neonserv_cmd_set_modes(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); +static char* neonserv_cmd_set_dynlimit(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); +static char* neonserv_cmd_set_nodelete(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument); #define NS_VALID_FUNCTION 0x01 #define NS_VALID_STRING 0x02 @@ -60,13 +61,67 @@ static const struct { {NULL, NULL, 0, NULL} }; +#define MAX_QUERY_LEN 1024 static CMD_BIND(neonserv_cmd_set) { int i, j; - if(argc && strcmp(argv[0], "help")) { - + if(argc && !strcmp(argv[0], "defaults")) { + //reset channel settings + int uaccess = getChannelAccess(user, chan, 1); + if(uaccess < 500) { + reply(getTextBot(), user, "NS_SET_DEFAULTS_OWNER", chan->name); + return; + } + int seed = 0; + static char defaultskey[16]; + for(tmp = user->auth; *tmp; tmp++) + seed = (seed * 0xEECE66DL ^ ((*tmp << 24) | (*tmp << 16) | (*tmp << 8) | *tmp)); + for(tmp = chan->name; *tmp; tmp++) + seed = (seed * 0xEECE66DL ^ ((*tmp << 24) | (*tmp << 16) | (*tmp << 8) | *tmp)); + sprintf(defaultskey, "%08x", seed); + if(argc > 1 && !strcmp(argv[1], defaultskey)) { + char query[MAX_QUERY_LEN]; + int querypos = 0; + check_mysql(); + i = 0; + while(channel_settings[i].setting) { + if(channel_settings[i].chanfield) + querypos += sprintf(query + querypos, "`%s` = NULL, ", channel_settings[i].chanfield); + i++; + } + if(querypos) { + query[querypos-2] = '\0'; + } + printf_mysql_query("UPDATE `channels` SET %s WHERE `channel_id` = '%d'", query, chan->channel_id); + reply(getTextBot(), user, "NS_SET_DEFAULTS_DONE", chan->name); + } else { + reply(getTextBot(), user, "NS_SET_DEFAULTS_CODE", chan->name, defaultskey); + } + } else if(argc && strcmp(argv[0], "help")) { + //find the correct command + i = 0; + j = 0; + while(channel_settings[i].setting) { + if(!stricmp(channel_settings[i].setting, argv[0])) { + //setting found + char *args = (argc > 1 ? merge_argv(argv, 1, argc) : NULL); + if(channel_settings[i].valid & NS_VALID_FUNCTION) { + neonserv_cmd_set_function *func = channel_settings[i].parameter; + func(client, user, chan, channel_settings[i].setting, args); + } else { + neonserv_cmd_set_setting(client, user, chan, channel_settings[i].setting, args); + } + j = 1; + break; + } + i++; + } + if(j == 0) { + //unknown setting + reply(getTextBot(), "NS_SET_UNKNOWN_SETTING", argv[0]); + } } else { check_mysql(); - char query[1024], *value, *org_value, *tmp, nameBuf[64]; + char query[MAX_QUERY_LEN], *value, *org_value, *tmp, nameBuf[64]; int querypos = 0; MYSQL_RES *res, *defaults_res; MYSQL_ROW row, defaults; @@ -95,7 +150,7 @@ static CMD_BIND(neonserv_cmd_set) { org_value = (row[j] ? row[j] : defaults[j]); } else if(channel_settings[i].valid & NS_VALID_FUNCTION) { neonserv_cmd_set_function *func = channel_settings[i].parameter; - org_value = func(client, user, chan, 0, NULL); + org_value = func(client, user, chan, NULL, NULL); } else org_value = "0"; value = org_value; @@ -134,19 +189,214 @@ static CMD_BIND(neonserv_cmd_set) { } } -static char* neonserv_cmd_set_trigger(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument) { - return "+"; +static void neonserv_cmd_set_setting(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int setting, char *argument) { + char *value; + char nameBuf[64]; + //get current value + MYSQL_RES *res; + MYSQL_ROW row; + check_mysql(); + printf_mysql_query("SELECT `%s` FROM `channels` WHERE `channel_id` = '%d'", channel_settings[setting].chanfield, chan->channel_id); + res = mysql_use(); + row = mysql_fetch_row(res); + if(row[0] == NULL) { + printf_mysql_query("SELECT `%s` FROM `channels` WHERE `channel_name` = 'defaults'", channel_settings[setting].chanfield); + res = mysql_use(); + row = mysql_fetch_row(res); + } + value = row[0]; + if(argument) { + //change the channel setting + //check the new argument + int valid = channel_settings[setting].valid; + if(valid & NS_VALID_STRING) { + if(!strcmp(argument, "*")) { + argument = ""; + } + } + if(valid & NS_VALID_ACCESS) { + int caccess = atoi(argument); + int max = ((valid & NS_VALID_NO501) ? 500 : 501); + if(caccess < 0 || caccess > max) { + reply(getTextBot(), user, "NS_INVALID_ACCESS", caccess); + return; + } + int uaccess = getChannelAccess(user, chan, 1); + if(uaccess == 500) uaccess++; + if(atoi(value) > uaccess) { + reply(getTextBot(), user, "NS_SET_CANNOT_SET"); + return; + } + if(caccess > uaccess) { + reply(getTextBot(), user, "NS_SET_BADLEVEL"); + return; + } + } + if(valid & NS_VALID_OPTIONS) { + int options = atoi((char *) channel_settings[setting].parameter); + int coption = atoi(argument); + if(coption < 0 || coption >= options) { + reply(getTextBot(), user, "NS_SET_INVALID_OPTION", argument); + int i; + int nameBufPos = 0; + if(valid & NS_HAS_OPT) { + for(i = 0; i < options; i++) { + sprintf(nameBuf, "NS_SET_OPTION_%s_%s", channel_settings[setting].setting, i); + reply(getTextBot(), user, "\002%d\002 - %s", i, get_language_string(user, nameBuf)); + } + } else { + for(i = 0; i < options; i++) { + nameBufPos += sprintf(nameBuf + nameBufPos, "\002%d\002, ", i); + } + if(nameBufPos) { + nameBuf[nameBufPos-2] = '\0'; + reply(getTextBot(), user, nameBuf); + } + } + return; + } + } + if(valid & NS_VALID_NUMERIC) { + sprintf(nameBuf, "%d", atoi(argument)); + argument = nameBuf; + } + if(valid & NS_VALID_BOOLEAN) { + if(!strcmp(argument, "0") || !strcmp(argument, "off") || !strcmp(argument, get_language_string(user, "NS_SET_OFF"))) { + argument = "0"; + } else if(!strcmp(argument, "0") || !strcmp(argument, "off") || !strcmp(argument, get_language_string(user, "NS_SET_OFF"))) { + argument = "1"; + } else { + reply(getTextBot(), user, "NS_SET_INVALID_BOOLEAN", argument); + return; + } + } + //valid - set it + value = argument; + printf_mysql_query("UPDATE `channels` SET `%s` = '%s' WHERE `channel_id` = '%d'", channel_settings[setting].chanfield, escape_string(value), chan->channel_id); + } + reply(getTextBot(), user, "\002%s\002 %s", channel_settings[setting].setting, value); + if(channel_settings[setting].valid & NS_HAS_HELP) { + sprintf(nameBuf, "NS_SET_HELP_%s", channel_settings[i].setting); + reply(getTextBot(), user, " %s", get_language_string(user, nameBuf); + } +} + +static char* neonserv_cmd_set_trigger(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument) { + char *trigger; + //get current trigger + MYSQL_RES *res; + MYSQL_ROW row; + check_mysql(); + printf_mysql_query("SELECT `trigger` FROM `bot_channels` WHERE `chanid` = '%d' AND `botid` = '%d'", chan->channel_id, client->clientid); + res = mysql_use(); + row = mysql_fetch_row(res); + trigger = row[0]; + if(argument) { + int uaccess = getChannelAccess(user, chan, 1); + if(uaccess < 500) { + reply(getTextBot(), user, "NS_SET_TRIGGER_OWNER", chan->name); + return NULL; + } + if(strlen(argument) > 15) + argument[15] = '\0'; + printf_mysql_query("UPDATE `bot_channels` SET `trigger` = '%s' WHERE `chanid` = '%d' AND `botid` = '%d'", escape_string(argument), chan->channel_id, client->clientid); + trigger = argument; + changeChannelTrigger(client->botid, chan, trigger); + } + if(setting) { + reply(getTextBot(), user, "\002%s\002 %s", setting, trigger); + } + return trigger; } -static char* neonserv_cmd_set_modes(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument) { - return NULL; +static char* neonserv_cmd_set_modes(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument) { + char *value; + //get current value + MYSQL_RES *res; + MYSQL_ROW row; + check_mysql(); + printf_mysql_query("SELECT `channel_modes` FROM `channels` WHERE `channel_id` = '%d'", chan->channel_id); + res = mysql_use(); + row = mysql_fetch_row(res); + if(row[0] == NULL) { + printf_mysql_query("SELECT `channel_modes` FROM `channels` WHERE `channel_name` = 'defaults'"); + res = mysql_use(); + row = mysql_fetch_row(res); + } + value = row[0]; + if(argument) { + //change the channel setting + //TODO: parse, check and set modelock + } + if(setting) { + reply(getTextBot(), user, "\002%s\002 %s", setting, value); + } + return value; } -static char* neonserv_cmd_set_dynlimit(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument) { - return NULL; +static char* neonserv_cmd_set_dynlimit(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument) { + char *value; + char tmp[64]; + //get current value + MYSQL_RES *res; + MYSQL_ROW row; + check_mysql(); + printf_mysql_query("SELECT `channel_dynlimit` FROM `channels` WHERE `channel_id` = '%d'", chan->channel_id); + res = mysql_use(); + row = mysql_fetch_row(res); + if(row[0] == NULL) { + printf_mysql_query("SELECT `channel_dynlimit` FROM `channels` WHERE `channel_name` = 'defaults'"); + res = mysql_use(); + row = mysql_fetch_row(res); + } + value = row[0]; + if(argument) { + //change the channel setting + sprintf(tmp, "%d", atoi(argument)); + argument = tmp; + printf_mysql_query("UPDATE `channels` SET `channel_dynlimit` = '%s' WHERE `channel_id` = '%d'", escape_string(argument), chan->channel_id); + if(strcmp(argument, "0")) + putsock(client, "MODE %s +l %d", chan->name, (chan->usercount + atoi(argument))); + else if(isModeSet(chan, 'l')) + putsock(client, "MODE %s -l", chan->name); + } + if(setting) { + reply(getTextBot(), user, "\002%s\002 %s", setting, value); + } + return value; } -static char* neonserv_cmd_set_nodelete(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, int set, char *argument) { - return NULL; +static char* neonserv_cmd_set_nodelete(struct ClientSocket *client, struct UserNode *user, struct ChanNode *chan, char *setting, char *argument) { + char *value; + //get current value + MYSQL_RES *res; + MYSQL_ROW row; + check_mysql(); + printf_mysql_query("SELECT `channel_nodelete` FROM `channels` WHERE `channel_id` = '%d'", chan->channel_id); + res = mysql_use(); + row = mysql_fetch_row(res); + if(row[0] == NULL) { + printf_mysql_query("SELECT `channel_nodelete` FROM `channels` WHERE `channel_name` = 'defaults'"); + res = mysql_use(); + row = mysql_fetch_row(res); + } + value = row[0]; + if(argument && isGodMode(user)) { + //change the channel setting + if(!strcmp(argument, "0") || !strcmp(argument, "off") || !strcmp(argument, get_language_string(user, "NS_SET_OFF"))) { + argument = "0"; + } else if(!strcmp(argument, "0") || !strcmp(argument, "off") || !strcmp(argument, get_language_string(user, "NS_SET_OFF"))) { + argument = "1"; + } else { + reply(getTextBot(), user, "NS_SET_INVALID_BOOLEAN", argument); + return NULL; + } + printf_mysql_query("UPDATE `channels` SET `channel_nodelete` = '%s' WHERE `channel_id` = '%d'", escape_string(argument), chan->channel_id); + } + if(setting) { + reply(getTextBot(), user, "\002%s\002 %s", setting, value); + } + return value; } +#undef MAX_QUERY_LEN -- 2.20.1