summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHaru <haru@dotalux.com>2015-01-22 01:06:07 +0100
committerHaru <haru@dotalux.com>2015-01-24 14:37:25 +0100
commitfe55c7980099b2813a182cdfcc571df705601a4a (patch)
tree367bbfe270fbb8ccdf31d57fe5b2714cf2ec46f6
parentfc50b63d454f59620e0d3ef6674bd9ae54a6175f (diff)
downloadhercules-fe55c7980099b2813a182cdfcc571df705601a4a.tar.gz
hercules-fe55c7980099b2813a182cdfcc571df705601a4a.tar.bz2
hercules-fe55c7980099b2813a182cdfcc571df705601a4a.tar.xz
hercules-fe55c7980099b2813a182cdfcc571df705601a4a.zip
Minor channel system refactoring
Signed-off-by: Haru <haru@dotalux.com>
-rw-r--r--src/map/atcommand.c90
-rw-r--r--src/map/channel.c190
-rw-r--r--src/map/channel.h18
-rw-r--r--src/map/clif.c2
-rw-r--r--src/map/guild.c8
-rwxr-xr-xtools/HPMHookGen/HPMHookGen.pl2
6 files changed, 203 insertions, 107 deletions
diff --git a/src/map/atcommand.c b/src/map/atcommand.c
index 60f0fc8ed..bf99d4c20 100644
--- a/src/map/atcommand.c
+++ b/src/map/atcommand.c
@@ -8649,7 +8649,7 @@ ACMD(join) {
clif->message(fd, atcmd_output);
return false;
}
- if( chan->pass[0] != '\0' && strcmp(chan->pass,pass) != 0 ) {
+ if( chan->password[0] != '\0' && strcmp(chan->password,pass) != 0 ) {
if( pc_has_permission(sd, PC_PERM_HCHSYS_ADMIN) ) {
sd->stealth = true;
} else {
@@ -8665,7 +8665,7 @@ ACMD(join) {
return false;
}
- if (!(chan->opt & HCS_OPT_ANNOUNCE_JOIN)) {
+ if (!(chan->options & HCS_OPT_ANNOUNCE_JOIN)) {
sprintf(atcmd_output, msg_txt(1403),name); // You're now in the '%s' channel
clif->message(fd, atcmd_output);
}
@@ -8767,13 +8767,11 @@ ACMD(channel) {
return false;
}
- CREATE(chan, struct channel_data, 1);
- channel->create(chan,sub1 + 1,sub2,0);
-
+ chan = channel->create(HCS_TYPE_PRIVATE, sub1 + 1, 0);
+ channel->set_password(chan, sub2);
chan->owner = sd->status.char_id;
- chan->type = HCS_TYPE_PRIVATE;
- if( !( chan->opt & HCS_OPT_ANNOUNCE_JOIN ) ) {
+ if( !( chan->options & HCS_OPT_ANNOUNCE_JOIN ) ) {
sprintf(atcmd_output, msg_txt(1403),sub1); // You're now in the '%s' channel
clif->message(fd, atcmd_output);
}
@@ -8911,8 +8909,8 @@ ACMD(channel) {
} else if (strcmpi(subcmd,"ban") == 0) {
// sub1 = channel name; sub2 = unused; sub3 = unused
struct map_session_data *pl_sd = NULL;
- struct channel_ban_entry *entry = NULL;
char sub4[NAME_LENGTH]; ///< player name
+ enum channel_operation_status ret = HCS_STATUS_OK;
if (sub1[0] != '#') {
clif->message(fd, msg_txt(1405));// Channel name must start with a '#'
@@ -8925,12 +8923,6 @@ ACMD(channel) {
return false;
}
- if (chan->owner != sd->status.char_id && !pc_has_permission(sd, PC_PERM_HCHSYS_ADMIN)) {
- sprintf(atcmd_output, msg_txt(1412), sub1);// You're not the owner of channel '%s'
- clif->message(fd, atcmd_output);
- return false;
- }
-
if (!message || !*message || sscanf(message, "%19s %19s %23[^\n]", subcmd, sub1, sub4) < 3) {
sprintf(atcmd_output, msg_txt(1434), sub4);// Player '%s' was not found
clif->message(fd, atcmd_output);
@@ -8943,25 +8935,24 @@ ACMD(channel) {
return false;
}
- if (pc_has_permission(pl_sd, PC_PERM_HCHSYS_ADMIN)) {
- clif->message(fd, msg_txt(1464)); // Ban failed, not possible to ban this user.
+ ret = channel->ban(chan, sd, pl_sd);
+
+ if (ret == HCS_STATUS_NOPERM) {
+ sprintf(atcmd_output, msg_txt(1412), sub1);// You're not the owner of channel '%s'
+ clif->message(fd, atcmd_output);
return false;
}
- if (chan->banned && idb_exists(chan->banned,pl_sd->status.account_id)) {
+ if (ret == HCS_STATUS_ALREADY) {
sprintf(atcmd_output, msg_txt(1465), pl_sd->status.name);// Player '%s' is already banned from this channel
clif->message(fd, atcmd_output);
return false;
}
- if (!chan->banned)
- chan->banned = idb_alloc(DB_OPT_BASE|DB_OPT_ALLOW_NULL_DATA|DB_OPT_RELEASE_DATA);
-
- CREATE(entry, struct channel_ban_entry, 1);
- safestrncpy(entry->name, pl_sd->status.name, NAME_LENGTH);
- idb_put(chan->banned, pl_sd->status.account_id, entry);
-
- channel->leave(chan,pl_sd);
+ if (ret != HCS_STATUS_OK/*ret == HCS_STATUS_FAIL*/) {
+ clif->message(fd, msg_txt(1464)); // Ban failed, not possible to ban this user.
+ return false;
+ }
sprintf(atcmd_output, msg_txt(1437),pl_sd->status.name,sub1); // Player '%s' has now been banned from '%s' channel
clif->message(fd, atcmd_output);
@@ -8969,6 +8960,7 @@ ACMD(channel) {
// sub1 = channel name; sub2 = unused; sub3 = unused
struct map_session_data *pl_sd = NULL;
char sub4[NAME_LENGTH]; ///< player name
+ enum channel_operation_status ret = HCS_STATUS_OK;
if (sub1[0] != '#') {
clif->message(fd, msg_txt(1405));// Channel name must start with a '#'
@@ -8979,42 +8971,33 @@ ACMD(channel) {
clif->message(fd, atcmd_output);
return false;
}
- if (chan->owner != sd->status.char_id && !pc_has_permission(sd, PC_PERM_HCHSYS_ADMIN)) {
- sprintf(atcmd_output, msg_txt(1412), sub1);// You're not the owner of channel '%s'
- clif->message(fd, atcmd_output);
- return false;
- }
- if (!chan->banned) {
- sprintf(atcmd_output, msg_txt(1439), sub1);// Channel '%s' has no banned players
+ if (!message || !*message || sscanf(message, "%19s %19s %23[^\n]", subcmd, sub1, sub4) < 3) {
+ sprintf(atcmd_output, msg_txt(1434), sub4);// Player '%s' was not found
clif->message(fd, atcmd_output);
return false;
}
- if (!message || !*message || sscanf(message, "%19s %19s %23[^\n]", subcmd, sub1, sub4) < 3) {
+ if (sub4[0] == '\0' || (pl_sd = map->nick2sd(sub4)) == NULL) {
sprintf(atcmd_output, msg_txt(1434), sub4);// Player '%s' was not found
clif->message(fd, atcmd_output);
return false;
}
- if (sub4[0] == '\0' || (pl_sd = map->nick2sd(sub4)) == NULL) {
- sprintf(atcmd_output, msg_txt(1434), sub4);// Player '%s' was not found
+ ret = channel->unban(chan, sd, pl_sd);
+ if (ret == HCS_STATUS_NOPERM) {
+ sprintf(atcmd_output, msg_txt(1412), sub1);// You're not the owner of channel '%s'
clif->message(fd, atcmd_output);
return false;
}
- if (!idb_exists(chan->banned,pl_sd->status.account_id)) {
+ if (ret == HCS_STATUS_ALREADY) {
sprintf(atcmd_output, msg_txt(1440), pl_sd->status.name);// Player '%s' is not banned from this channel
clif->message(fd, atcmd_output);
return false;
}
- idb_remove(chan->banned, pl_sd->status.account_id);
- if (!db_size(chan->banned)) {
- db_destroy(chan->banned);
- chan->banned = NULL;
- }
-
sprintf(atcmd_output, msg_txt(1441),pl_sd->status.name,sub1); // Player '%s' has now been unbanned from the '%s' channel
clif->message(fd, atcmd_output);
} else if (strcmpi(subcmd,"unbanall") == 0) {
+ enum channel_operation_status ret = HCS_STATUS_OK;
// sub1 = channel name; sub2 = unused; sub3 = unused
if (sub1[0] != '#') {
clif->message(fd, msg_txt(1405));// Channel name must start with a '#'
@@ -9025,18 +9008,17 @@ ACMD(channel) {
clif->message(fd, atcmd_output);
return false;
}
- if (chan->owner != sd->status.char_id && !pc_has_permission(sd, PC_PERM_HCHSYS_ADMIN)) {
+ ret = channel->unban(chan, sd, NULL);
+ if (ret == HCS_STATUS_NOPERM) {
sprintf(atcmd_output, msg_txt(1412), sub1);// You're not the owner of channel '%s'
clif->message(fd, atcmd_output);
return false;
}
- if (!chan->banned) {
+ if (ret == HCS_STATUS_ALREADY) {
sprintf(atcmd_output, msg_txt(1439), sub1);// Channel '%s' has no banned players
clif->message(fd, atcmd_output);
return false;
}
- db_destroy(chan->banned);
- chan->banned = NULL;
sprintf(atcmd_output, msg_txt(1442),sub1); // Removed all bans from '%s' channel
clif->message(fd, atcmd_output);
@@ -9124,12 +9106,12 @@ ACMD(channel) {
sprintf(atcmd_output, msg_txt(1466), opt_str[k]);// For '%s' you need the amount of seconds (from 0 to 10)
clif->message(fd, atcmd_output);
return false;
- } else if (chan->opt & k) {
+ } else if (chan->options & k) {
sprintf(atcmd_output, msg_txt(1449), opt_str[k],opt_str[k]); // option '%s' is already enabled, if you'd like to disable it type '@channel setopt %s 0'
clif->message(fd, atcmd_output);
return false;
} else {
- chan->opt |= k;
+ channel->set_options(chan, chan->options | k);
sprintf(atcmd_output, msg_txt(1450), opt_str[k],chan->name);//option '%s' is now enabled for channel '%s'
clif->message(fd, atcmd_output);
return true;
@@ -9143,13 +9125,13 @@ ACMD(channel) {
return false;
}
if (v == 0) {
- chan->opt &=~ k;
+ channel->set_options(chan, chan->options&~k);
chan->msg_delay = 0;
sprintf(atcmd_output, msg_txt(1453), opt_str[k],chan->name,v);// option '%s' is now disabled for channel '%s'
clif->message(fd, atcmd_output);
return true;
} else {
- chan->opt |= k;
+ channel->set_options(chan, chan->options | k);
chan->msg_delay = v;
sprintf(atcmd_output, msg_txt(1452), opt_str[k],chan->name,v);// option '%s' is now enabled for channel '%s' with %d seconds
clif->message(fd, atcmd_output);
@@ -9157,22 +9139,22 @@ ACMD(channel) {
}
} else {
if (v) {
- if (chan->opt & k) {
+ if (chan->options & k) {
sprintf(atcmd_output, msg_txt(1449), opt_str[k],opt_str[k]); // option '%s' is already enabled, if you'd like to disable it type '@channel opt %s 0'
clif->message(fd, atcmd_output);
return false;
} else {
- chan->opt |= k;
+ channel->set_options(chan, chan->options | k);
sprintf(atcmd_output, msg_txt(1454), opt_str[k],chan->name);//option '%s' is now enabled for channel '%s'
clif->message(fd, atcmd_output);
}
} else {
- if (!(chan->opt & k)) {
+ if (!(chan->options & k)) {
sprintf(atcmd_output, msg_txt(1454), opt_str[k],chan->name); // option '%s' is not enabled on channel '%s'
clif->message(fd, atcmd_output);
return false;
} else {
- chan->opt &=~ k;
+ channel->set_options(chan, chan->options&~k);
sprintf(atcmd_output, msg_txt(1453), opt_str[k],chan->name);// option '%s' is now disabled for channel '%s'
clif->message(fd, atcmd_output);
return true;
diff --git a/src/map/channel.c b/src/map/channel.c
index 6ebe4650d..b0640eeff 100644
--- a/src/map/channel.c
+++ b/src/map/channel.c
@@ -19,6 +19,7 @@
#include "../common/conf.h"
#include "../common/db.h"
#include "../common/malloc.h"
+#include "../common/nullpo.h"
#include "../common/random.h"
#include "../common/showmsg.h"
#include "../common/socket.h"
@@ -30,24 +31,142 @@ struct channel_interface channel_s;
static struct Channel_Config channel_config;
-void channel_create(struct channel_data *chan, char *name, char *pass, unsigned char color)
+/**
+ * Creates a chat channel.
+ *
+ * If the channel type isn't HCS_TYPE_MAP or HCS_TYPE_ALLY, the channel is added to the channel->db.
+ *
+ * @param type The channel type.
+ * @param name The channel name.
+ * @param color The channel chat color.
+ * @return A pointer to the created channel.
+ */
+struct channel_data *channel_create(enum channel_types type, const char *name, unsigned char color)
{
+ struct channel_data *chan;
+ CREATE(chan, struct channel_data, 1);
chan->users = idb_alloc(DB_OPT_BASE);
if (name)
safestrncpy(chan->name, name, HCS_NAME_LENGTH);
chan->color = color;
- if (!pass)
- chan->pass[0] = '\0';
- else
- safestrncpy(chan->pass, pass, HCS_NAME_LENGTH);
- chan->opt = HCS_OPT_BASE;
+ chan->options = HCS_OPT_BASE;
chan->banned = NULL;
chan->msg_delay = 0;
+ chan->type = type;
if (chan->type != HCS_TYPE_MAP && chan->type != HCS_TYPE_ALLY)
strdb_put(channel->db, chan->name, chan);
+ return chan;
+}
+
+/**
+ * Sets a chat channel password.
+ *
+ * @param chan The channel to edit.
+ * @param pass The password to set. Pass NULL to remove existing passwords.
+ */
+void channel_set_password(struct channel_data *chan, const char *password)
+{
+ nullpo_retv(chan);
+ if (password)
+ safestrncpy(chan->password, password, HCS_NAME_LENGTH);
+ else
+ chan->password[0] = '\0';
+}
+
+/**
+ * Bans a character from the given channel.
+ *
+ * @param chan The channel.
+ * @param ssd The source character, if any.
+ * @param tsd The target character.
+ * @retval HCS_STATUS_OK if the operation succeeded.
+ * @retval HCS_STATUS_ALREADY if the target character is already banned.
+ * @retval HCS_STATUS_NOPERM if the source character doesn't have enough permissions.
+ * @retval HCS_STATUS_FAIL in case of generic failure.
+ */
+enum channel_operation_status channel_ban(struct channel_data *chan, const struct map_session_data *ssd, struct map_session_data *tsd)
+{
+ struct channel_ban_entry *entry = NULL;
+
+ nullpo_retr(HCS_STATUS_FAIL, chan);
+ nullpo_retr(HCS_STATUS_FAIL, tsd);
+
+ if (ssd && chan->owner != ssd->status.char_id && !pc_has_permission(ssd, PC_PERM_HCHSYS_ADMIN))
+ return HCS_STATUS_NOPERM;
+
+ if (pc_has_permission(tsd, PC_PERM_HCHSYS_ADMIN))
+ return HCS_STATUS_FAIL;
+
+ if (chan->banned && idb_exists(chan->banned, tsd->status.account_id))
+ return HCS_STATUS_ALREADY;
+
+ if (!chan->banned)
+ chan->banned = idb_alloc(DB_OPT_BASE|DB_OPT_ALLOW_NULL_DATA|DB_OPT_RELEASE_DATA);
+
+ CREATE(entry, struct channel_ban_entry, 1);
+ safestrncpy(entry->name, tsd->status.name, NAME_LENGTH);
+ idb_put(chan->banned, tsd->status.account_id, entry);
+
+ channel->leave(chan, tsd);
+
+ return HCS_STATUS_OK;
+}
+
+/**
+ * Unbans a character from the given channel.
+ *
+ * @param chan The channel.
+ * @param ssd The source character, if any.
+ * @param tsd The target character. If no target character is specified, all characters are unbanned.
+ * @retval HCS_STATUS_OK if the operation succeeded.
+ * @retval HCS_STATUS_ALREADY if the target character is not banned.
+ * @retval HCS_STATUS_NOPERM if the source character doesn't have enough permissions.
+ * @retval HCS_STATUS_FAIL in case of generic failure.
+ */
+enum channel_operation_status channel_unban(struct channel_data *chan, const struct map_session_data *ssd, struct map_session_data *tsd)
+{
+ nullpo_retr(HCS_STATUS_FAIL, chan);
+
+ if (ssd && chan->owner != ssd->status.char_id && !pc_has_permission(ssd, PC_PERM_HCHSYS_ADMIN))
+ return HCS_STATUS_NOPERM;
+
+ if (!chan->banned)
+ return HCS_STATUS_ALREADY;
+
+ if (!tsd) {
+ // Unban all
+ db_destroy(chan->banned);
+ chan->banned = NULL;
+ return HCS_STATUS_OK;
+ }
+
+ // Unban one
+ if (!idb_exists(chan->banned, tsd->status.account_id))
+ return HCS_STATUS_ALREADY;
+
+ idb_remove(chan->banned, tsd->status.account_id);
+ if (!db_size(chan->banned)) {
+ db_destroy(chan->banned);
+ chan->banned = NULL;
+ }
+
+ return HCS_STATUS_OK;
+}
+
+/**
+ * Sets or edits a channel's options.
+ *
+ * @param chan The channel.
+ * @param options The new options set to apply.
+ */
+void channel_set_options(struct channel_data *chan, unsigned int options)
+{
+ nullpo_retv(chan);
+
+ chan->options = options;
}
/**
@@ -87,7 +206,7 @@ void channel_join(struct channel_data *chan, struct map_session_data *sd)
if (sd->stealth) {
sd->stealth = false;
- } else if (chan->opt & HCS_OPT_ANNOUNCE_JOIN) {
+ } else if (chan->options & HCS_OPT_ANNOUNCE_JOIN) {
char message[60];
sprintf(message, "#%s '%s' joined",chan->name,sd->status.name);
clif->channel_msg(chan,sd,message);
@@ -102,28 +221,23 @@ void channel_join(struct channel_data *chan, struct map_session_data *sd)
void channel_map_join(struct map_session_data *sd)
{
- if( sd->state.autotrade || sd->state.standalone )
+ if (sd->state.autotrade || sd->state.standalone)
return;
- if( !map->list[sd->bl.m].channel ) {
-
- if (map->list[sd->bl.m].flag.chsysnolocalaj || (map->list[sd->bl.m].instance_id >= 0 && instance->list[map->list[sd->bl.m].instance_id].owner_type != IOT_NONE) )
+ if (!map->list[sd->bl.m].channel) {
+ if (map->list[sd->bl.m].flag.chsysnolocalaj || (map->list[sd->bl.m].instance_id >= 0 && instance->list[map->list[sd->bl.m].instance_id].owner_type != IOT_NONE))
return;
- CREATE(map->list[sd->bl.m].channel, struct channel_data , 1);
- safestrncpy(map->list[sd->bl.m].channel->name, channel->config->local_name, HCS_NAME_LENGTH);
- map->list[sd->bl.m].channel->type = HCS_TYPE_MAP;
+ map->list[sd->bl.m].channel = channel->create(HCS_TYPE_MAP, channel->config->local_name, channel->config->local_color);
map->list[sd->bl.m].channel->m = sd->bl.m;
-
- channel->create(map->list[sd->bl.m].channel, NULL, NULL, channel->config->local_color);
}
- if( map->list[sd->bl.m].channel->banned && idb_exists(map->list[sd->bl.m].channel->banned, sd->status.account_id) ) {
+ if (map->list[sd->bl.m].channel->banned && idb_exists(map->list[sd->bl.m].channel->banned, sd->status.account_id)) {
return;
}
channel->join(map->list[sd->bl.m].channel,sd);
- if( !( map->list[sd->bl.m].channel->opt & HCS_OPT_ANNOUNCE_JOIN ) ) {
+ if (!( map->list[sd->bl.m].channel->options & HCS_OPT_ANNOUNCE_JOIN )) {
char mout[60];
sprintf(mout, msg_txt(1435), channel->config->local_name, map->list[sd->bl.m].name); // You're now in the '#%s' channel for '%s'
clif->colormes(sd->fd, COLOR_DEFAULT, mout);
@@ -142,7 +256,7 @@ void channel_leave(struct channel_data *chan, struct map_session_data *sd)
if( !db_size(chan->users) && chan->type == HCS_TYPE_PRIVATE ) {
channel->delete(chan);
- } else if( !channel->config->closing && (chan->opt & HCS_OPT_ANNOUNCE_JOIN) ) {
+ } else if( !channel->config->closing && (chan->options & HCS_OPT_ANNOUNCE_JOIN) ) {
char message[60];
sprintf(message, "#%s '%s' left",chan->name,sd->status.name);
clif->channel_msg(chan,sd,message);
@@ -188,7 +302,7 @@ void channel_quit_guild(struct map_session_data *sd)
if (!db_size(chan->users) && chan->type == HCS_TYPE_PRIVATE) {
channel->delete(chan);
- } else if (!channel->config->closing && (chan->opt & HCS_OPT_ANNOUNCE_JOIN)) {
+ } else if (!channel->config->closing && (chan->options & HCS_OPT_ANNOUNCE_JOIN)) {
char message[60];
sprintf(message, "#%s '%s' left",chan->name,sd->status.name);
clif->channel_msg(chan,sd,message);
@@ -230,7 +344,7 @@ void channel_quit(struct map_session_data *sd)
if (!db_size(chan->users) && chan->type == HCS_TYPE_PRIVATE) {
channel->delete(chan);
- } else if (!channel->config->closing && (chan->opt & HCS_OPT_ANNOUNCE_JOIN)) {
+ } else if (!channel->config->closing && (chan->options & HCS_OPT_ANNOUNCE_JOIN)) {
char message[60];
sprintf(message, "#%s '%s' left",chan->name,sd->status.name);
clif->channel_msg(chan,sd,message);
@@ -512,14 +626,7 @@ void read_channels_config(void)
}
if (channel->config->irc) {
- struct channel_data *chd;
- CREATE(chd, struct channel_data, 1);
-
- safestrncpy(chd->name, channel->config->irc_name, HCS_NAME_LENGTH);
- chd->type = HCS_TYPE_IRC;
-
- channel->create(chd, NULL, NULL, channel->config->irc_color);
- ircbot->channel = chd;
+ ircbot->channel = channel->create(HCS_TYPE_IRC, channel->config->irc_name, channel->config->irc_color);
}
if( (channels = libconfig->setting_get_member(settings, "default_channels")) != NULL ) {
@@ -529,27 +636,21 @@ void read_channels_config(void)
config_setting_t *chan = libconfig->setting_get_elem(channels, i);
const char *name = config_setting_name(chan);
const char *color = libconfig->setting_get_string_elem(channels,i);
- struct channel_data *chd;
- for (k = 0; k < channel->config->colors_count; k++) {
- if (strcmpi(channel->config->colors_name[k],color) == 0)
- break;
- }
- if( k == channel->config->colors_count) {
+ ARR_FIND(0, channel->config->colors_count, k, strcmpi(channel->config->colors_name[k],color) == 0);
+ if (k == channel->config->colors_count) {
ShowError("channels.conf: unknown color '%s' for channel '%s', skipping channel...\n",color,name);
continue;
}
- if( strcmpi(name, channel->config->local_name) == 0 || strcmpi(name, channel->config->ally_name) == 0 || strcmpi(name, channel->config->irc_name) == 0 || strdb_exists(channel->db, name) ) {
+ if (strcmpi(name, channel->config->local_name) == 0
+ || strcmpi(name, channel->config->ally_name) == 0
+ || strcmpi(name, channel->config->irc_name) == 0
+ || strdb_exists(channel->db, name)) {
ShowError("channels.conf: duplicate channel '%s', skipping channel...\n",name);
continue;
}
- CREATE( chd, struct channel_data, 1 );
-
- safestrncpy(chd->name, name, HCS_NAME_LENGTH);
- chd->type = HCS_TYPE_PUBLIC;
-
- channel->create(chd,NULL,NULL,k);
+ channel->create(HCS_TYPE_PUBLIC, name, k);
}
}
@@ -605,6 +706,11 @@ void channel_defaults(void)
channel->config = &channel_config;
channel->create = channel_create;
+ channel->set_password = channel_set_password;
+ channel->ban = channel_ban;
+ channel->unban = channel_unban;
+ channel->set_options = channel_set_options;
+
channel->send = channel_send;
channel->join = channel_join;
channel->leave = channel_leave;
diff --git a/src/map/channel.h b/src/map/channel.h
index dd434d0cc..11ba968a9 100644
--- a/src/map/channel.h
+++ b/src/map/channel.h
@@ -35,6 +35,13 @@ enum channel_types {
HCS_TYPE_IRC = 4,
};
+enum channel_operation_status {
+ HCS_STATUS_OK = 0,
+ HCS_STATUS_FAIL,
+ HCS_STATUS_ALREADY,
+ HCS_STATUS_NOPERM,
+};
+
/**
* Structures
**/
@@ -59,11 +66,11 @@ struct channel_ban_entry {
struct channel_data {
char name[HCS_NAME_LENGTH];
- char pass[HCS_NAME_LENGTH];
+ char password[HCS_NAME_LENGTH];
unsigned char color;
DBMap *users;
DBMap *banned;
- unsigned int opt;
+ unsigned int options;
unsigned int owner;
enum channel_types type;
uint16 m;
@@ -78,7 +85,12 @@ struct channel_interface {
int (*init) (bool minimal);
void (*final) (void);
- void (*create) (struct channel_data *chan, char *name, char *pass, unsigned char color);
+ struct channel_data *(*create) (enum channel_types type, const char *name, unsigned char color);
+ void (*set_password) (struct channel_data *chan, const char *password);
+ enum channel_operation_status (*ban) (struct channel_data *chan, const struct map_session_data *ssd, struct map_session_data *tsd);
+ enum channel_operation_status (*unban) (struct channel_data *chan, const struct map_session_data *ssd, struct map_session_data *tsd);
+ void (*set_options) (struct channel_data *chan, unsigned int options);
+
void (*send) (struct channel_data *chan, struct map_session_data *sd, const char *msg);
void (*join) (struct channel_data *chan, struct map_session_data *sd);
void (*leave) (struct channel_data *chan, struct map_session_data *sd);
diff --git a/src/map/clif.c b/src/map/clif.c
index cd449fc5a..10ab7121a 100644
--- a/src/map/clif.c
+++ b/src/map/clif.c
@@ -10064,7 +10064,7 @@ void clif_parse_WisMessage(int fd, struct map_session_data* sd)
}
if( k < sd->channel_count ) {
channel->send(chan,sd,message);
- } else if( chan->pass[0] == '\0' && !(chan->banned && idb_exists(chan->banned, sd->status.account_id)) ) {
+ } else if( chan->password[0] == '\0' && !(chan->banned && idb_exists(chan->banned, sd->status.account_id)) ) {
if( chan->type == HCS_TYPE_ALLY ) {
struct guild *g = sd->guild;
for (k = 0; k < MAX_GUILDALLIANCE; k++) {
diff --git a/src/map/guild.c b/src/map/guild.c
index 2ee76ba98..3e71e99dc 100644
--- a/src/map/guild.c
+++ b/src/map/guild.c
@@ -472,13 +472,7 @@ int guild_recv_info(struct guild *sg) {
g->instances = 0;
idb_put(guild->db,sg->guild_id,g);
if (channel->config->ally) {
- struct channel_data *chan;
-
- CREATE(chan, struct channel_data , 1);
- safestrncpy(chan->name, channel->config->ally_name, HCS_NAME_LENGTH);
- chan->type = HCS_TYPE_ALLY;
-
- channel->create(chan, NULL, NULL, channel->config->ally_color);
+ struct channel_data *chan = channel->create(HCS_TYPE_ALLY, channel->config->ally_name, channel->config->ally_color);
if (channel->config->ally_autojoin) {
struct s_mapiterator* iter = mapit_getallusers();
struct guild *tg[MAX_GUILDALLIANCE];
diff --git a/tools/HPMHookGen/HPMHookGen.pl b/tools/HPMHookGen/HPMHookGen.pl
index 03b32394c..4fa548e44 100755
--- a/tools/HPMHookGen/HPMHookGen.pl
+++ b/tools/HPMHookGen/HPMHookGen.pl
@@ -217,6 +217,8 @@ sub parse($$) {
$rtinit = ' = BL_NUL';
} elsif ($x =~ /^enum\s+homun_type$/) { # Known enum homun_type
$rtinit = ' = HT_INVALID';
+ } elsif ($x =~ /^enum\s+channel_operation_status$/) { # Known enum channel_operation_status
+ $rtinit = ' = HCS_STATUS_FAIL';
} elsif ($x =~ /^enum\s+bg_queue_types$/) { # Known enum bg_queue_types
$rtinit = ' = BGQT_INVALID';
} elsif ($x =~ /^struct\s+.*$/ or $x eq 'DBData') { # Structs