/* -------------------------------------------------------------------------- * * -------------------------------------------------------------------------- */ static int cm_op_hook(struct list *lptr, struct chanuser *cuptr) { cuptr->flags |= CHFLG(o); chanmode_prefix_make(cuptr->prefix, cuptr->flags); chanmode_change_add(lptr, CHANMODE_ADD, 'o', NULL, cuptr); return 0; }
/* -------------------------------------------------------------------------- * * -------------------------------------------------------------------------- */ static int cm_op_kick(struct lclient *lcptr, struct client *cptr, struct channel *chptr, struct chanuser *cuptr, struct chanuser *acuptr, const char *reason) { if(cuptr) { if(cuptr->flags & CHFLG(o)) return 1; } return 0; }
/* -------------------------------------------------------------------------- * * -------------------------------------------------------------------------- */ static int cm_noext_hook(struct client *cptr, struct channel *chptr, intptr_t type, const char *text) { struct chanuser *cuptr = chanuser_find(chptr, cptr); if(cuptr == NULL && (chptr->modes & CHFLG(n))) { numeric_send(cptr, ERR_CANNOTSENDTOCHAN, chptr->name); return 1; } return 0; }
struct channel *chptr, struct chanuser *cuptr, struct chanuser *acuptr, const char *reason); /* -------------------------------------------------------------------------- * * * -------------------------------------------------------------------------- */ static const char *cm_op_help[] = { "+o <nickname> Chanop status. Chanops have full control of a channel.", " They can set modes and the topic and kick members.", NULL }; static struct chanmode cm_op_mode = { CM_OP_CHAR, /* Mode character */ '@', /* Privilege prefix */ CHANMODE_TYPE_PRIVILEGE, /* Channel mode is a privilege */ CHFLG(o), /* Only OPs can change the privilege */ 100, /* Sorting order */ chanuser_mode_bounce, /* Bounce handler */ cm_op_help /* Help text */ }; /* -------------------------------------------------------------------------- * * Module hooks * * -------------------------------------------------------------------------- */ int cm_op_load(void) { /* register the channel mode */ if(chanmode_register(&cm_op_mode) == NULL) return -1; hook_register(channel_join, HOOK_2ND, cm_op_hook);
static void cm_ban_hook(struct client *cptr, struct channel *chptr, const char *key, int *reply); /* -------------------------------------------------------------------------- * * Set up the channel mode structure * * -------------------------------------------------------------------------- */ static const char *cm_ban_help[] = { "+b <mask> Users matching the mask are banned from the channel.", NULL }; static struct chanmode cm_ban_mode = { CM_BAN_CHAR, /* mode character */ '\0', /* no prefix, because its not a privilege */ CHANMODE_TYPE_LIST, /* channel mode is a list */ CHFLG(o) | CHFLG(h), /* only OPs and Halfops can change the modelist */ RPL_BANLIST, /* use this reply when dumping modelist */ chanmode_bounce_ban, /* bounce handler */ cm_ban_help /* help text */ }; /* -------------------------------------------------------------------------- * * Module hooks * * -------------------------------------------------------------------------- */ int cm_ban_load(void) { /* register the channel mode */ if(chanmode_register(&cm_ban_mode) == NULL) return -1; /* register a hook in channel_join */
/* -------------------------------------------------------------------------- * * argv[0] - prefix * * argv[1] - 'ntopic' * * argv[2] - channel * * argv[3] - channel ts * * argv[4] - topic info * * argv[5] - topic time * * argv[6] - topic * * -------------------------------------------------------------------------- */ static void ms_ntopic(struct lclient *lcptr, struct client *cptr, int argc, char **argv) { struct channel *chptr; time_t ts; time_t topic_ts; int changed = 0; char topic[IRCD_TOPICLEN]; topic[0] = '\0'; if(argc == 7) strlcpy(topic, argv[6], sizeof(topic)); if((chptr = channel_find_name(argv[2])) == NULL) { log(client_log, L_warning, "Dropping invalid NTOPIC for channel %s.", argv[2]); return; } ts = str_toul(argv[3], NULL, 10); if(ts > chptr->ts || chptr->topic[0]) { log(client_log, L_verbose, "Dropping NTOPIC for %s with too recent TS", chptr->name); return; } topic_ts = str_toul(argv[5], NULL, 10); if(chptr->ts == ts) { if(chptr->topic_ts > topic_ts) { log(client_log, L_verbose, "Dropping NTOPIC for %s because its older", chptr->name); return; } if(chptr->topic_ts == topic_ts) { size_t nlen; size_t olen; nlen = topic[0] ? str_len(topic) : 0; olen = str_len(chptr->topic); if(nlen < olen) { log(client_log, L_warning, "TOPIC collision on %s, ignoring.", chptr->name); return; } if(nlen == olen) { if((topic == NULL && chptr->topic[0] == '\0')) return; if(!str_cmp(topic, chptr->topic)) return; } } } if(chptr->ts != ts) { log(channel_log, L_warning, "TS for channel %s changed from %lu to %lu.", chptr->name, chptr->ts, ts); chptr->ts = ts; } if(str_cmp(chptr->topic, topic)) changed = 1; if(changed) { if(topic[0]) strlcpy(chptr->topic, topic, sizeof(chptr->topic)); else chptr->topic[0] = '\0'; } strlcpy(chptr->topic_info, argv[4], sizeof(chptr->topic_info)); chptr->topic_ts = topic_ts; if(chptr->topic[0]) server_send(lcptr, NULL, CAP_NONE, CAP_NONE, ":%C NTOPIC %s %lu %s %lu :%s", cptr, chptr->name, chptr->ts, chptr->topic_info, chptr->topic_ts, chptr->topic); else server_send(lcptr, NULL, CAP_NONE, CAP_NONE, ":%C NTOPIC %s %lu %s %lu", cptr, chptr->name, chptr->ts, chptr->topic_info, chptr->topic_ts); if(changed) { channel_send(NULL, chptr, CHFLG(NONE), CHFLG(NONE), ":%C TOPIC %s :%s", cptr, chptr->name, chptr->topic); } }
intptr_t type, const char *text); /* -------------------------------------------------------------------------- * * -------------------------------------------------------------------------- */ static const char *cm_noext_help[] = { "+n No external messages. Only members can send to the channel.", NULL }; static struct chanmode cm_noext_mode = { CM_NOEXT_CHAR, /* mode character */ '\0', /* no prefix, because its not a privilege */ CHANMODE_TYPE_SINGLE, /* channel mode is a single flag */ CHFLG(o) | CHFLG(h), /* only OPs and Halfops can change the flag */ 0, /* no order and no reply */ chanmode_bounce_simple, /* bounce handler */ cm_noext_help /* help text */ }; /* -------------------------------------------------------------------------- * * Module hooks * * -------------------------------------------------------------------------- */ int cm_noext_load(void) { /* register the channel mode */ if(chanmode_register(&cm_noext_mode) == NULL) return -1; hook_register(channel_message, HOOK_DEFAULT, cm_noext_hook);