diff options
-rw-r--r-- | include/mode.h | 11 | ||||
-rw-r--r-- | include/users.h | 32 | ||||
-rw-r--r-- | src/cmd_die.cpp | 2 | ||||
-rw-r--r-- | src/cmd_oper.cpp | 5 | ||||
-rw-r--r-- | src/command_parse.cpp | 17 | ||||
-rw-r--r-- | src/helperfuncs.cpp | 10 | ||||
-rw-r--r-- | src/message.cpp | 6 | ||||
-rw-r--r-- | src/modules/extra/m_sqloper.cpp | 4 | ||||
-rw-r--r-- | src/modules/m_botmode.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_cban.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_censor.cpp | 4 | ||||
-rw-r--r-- | src/modules/m_check.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_helpop.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_park.cpp | 4 | ||||
-rw-r--r-- | src/modules/m_services.cpp | 10 | ||||
-rw-r--r-- | src/modules/m_services_account.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_showwhois.cpp | 2 | ||||
-rw-r--r-- | src/modules/m_spanningtree.cpp | 27 | ||||
-rw-r--r-- | src/modules/m_stripcolor.cpp | 2 | ||||
-rw-r--r-- | src/users.cpp | 5 |
20 files changed, 66 insertions, 85 deletions
diff --git a/include/mode.h b/include/mode.h index 170da92d5..59dc9dc3b 100644 --- a/include/mode.h +++ b/include/mode.h @@ -30,17 +30,6 @@ #include "ctables.h" /** - * This enum contains a set of bitmasks which - * are used to compress the 'standard' usermodes - * +isw into a bitfield for fast checking. - */ -enum UserModeBits { - UM_INVISIBLE = 1, - UM_SERVERNOTICE = 2, - UM_WALLOPS = 4 -}; - -/** * Holds the values for different type of modes * that can exist, USER or CHANNEL type. */ diff --git a/include/users.h b/include/users.h index 0d812c0a4..30e524e85 100644 --- a/include/users.h +++ b/include/users.h @@ -43,6 +43,15 @@ enum ClassTypes { CC_DENY = 1 }; +/** RFC1459 channel modes + * */ +enum ChannelModes { + UM_SERVERNOTICE = 's'-65, + UM_WALLOPS = 'w'-65, + UM_INVISIBLE = 'i'-65, + UM_OPERATOR = 'o'-65, +}; + /** Holds a channel name to which a user has been invited. */ class Invited : public classbase @@ -150,22 +159,17 @@ class userrec : public connection */ char fullname[MAXGECOS+1]; - /** The user's mode string. - * This may contain any of the following RFC characters: o, w, s, i - * Your module may define other mode characters as it sees fit. - * it is limited to length 54, as there can only be a maximum of 52 - * user modes (26 upper, 26 lower case) a null terminating char, and - * an optional + character. + /** The user's mode list. + * This is NOT a null terminated string! In the 1.1 version of InspIRCd + * this is an array of values in a similar way to channel modes. + * A value of 1 in field (modeletter-65) indicates that the mode is + * set, for example, to work out if mode +s is set, we check the field + * userrec::modes['s'-65] != 0. + * The following RFC characters o, w, s, i have constants defined via an + * enum, such as UM_SERVERNOTICE and UM_OPETATOR. */ - char modes[54]; + char modes[64]; - /** This contains a bitmask of the RFC modes +swi, - * which can be used for fast lookup when iterating all the users. - * It is maintained by the mode parser and matches the character - * modes stored in 'modes'. - */ - char modebits; - UserChanList chans; /** The server the user is connected to. diff --git a/src/cmd_die.cpp b/src/cmd_die.cpp index c5514c067..494eba0c5 100644 --- a/src/cmd_die.cpp +++ b/src/cmd_die.cpp @@ -40,7 +40,7 @@ void cmd_die::Handle (char **parameters, int pcnt, userrec *user) { userrec* a = *i; - if (IS_LOCAL(a) && (a->modebits & UM_SERVERNOTICE)) + if (IS_LOCAL(a) && (a->modes[UM_SERVERNOTICE])) { WriteServ(a->fd, "NOTICE %s :*** DIE command from %s!%s@%s, terminating...", a->nick, a->nick, a->ident, a->host); a->FlushWriteBuf(); diff --git a/src/cmd_oper.cpp b/src/cmd_oper.cpp index a209c7e64..e19281cbf 100644 --- a/src/cmd_oper.cpp +++ b/src/cmd_oper.cpp @@ -115,9 +115,10 @@ void cmd_oper::Handle (char **parameters, int pcnt, userrec *user) /* correct oper credentials */ WriteOpers("*** %s (%s@%s) is now an IRC operator of type %s",user->nick,user->ident,user->host,OperType); WriteServ(user->fd,"381 %s :You are now an IRC operator of type %s",user->nick,OperType); - if (!strchr(user->modes,'o')) + if (!user->modes[UM_OPERATOR]) { - strcat(user->modes,"o"); + user->modes[UM_OPERATOR] = 1; + ModeParser::BuildModeString(user); WriteServ(user->fd,"MODE %s :+o",user->nick); FOREACH_MOD(I_OnOper,OnOper(user,OperType)); log(DEFAULT,"OPER: %s!%s@%s opered as type: %s",user->nick,user->ident,user->host,OperType); diff --git a/src/command_parse.cpp b/src/command_parse.cpp index 7a26f209b..befcde7ca 100644 --- a/src/command_parse.cpp +++ b/src/command_parse.cpp @@ -306,7 +306,7 @@ bool CommandParser::IsValidCommand(const std::string &commandname, int pcnt, use { if ((pcnt>=n->second->min_params) && (n->second->source != "<core>")) { - if ((strchr(user->modes,n->second->flags_needed)) || (!n->second->flags_needed)) + if ((!n->second->flags_needed) || (user->modes[n->second->flags_needed-65])) { if (n->second->flags_needed) { @@ -329,7 +329,7 @@ bool CommandParser::CallHandler(const std::string &commandname,char **parameters { if (pcnt >= n->second->min_params) { - if ((strchr(user->modes,n->second->flags_needed)) || (!n->second->flags_needed)) + if ((!n->second->flags_needed) || (user->modes[n->second->flags_needed-65])) { if (n->second->flags_needed) { @@ -603,12 +603,15 @@ void CommandParser::ProcessCommand(userrec *user, char* cmd) WriteServ(user->fd,"461 %s %s :Not enough parameters",user->nick,command); return; } - if ((!strchr(user->modes,cm->second->flags_needed)) && (cm->second->flags_needed)) + if (cm->second->flags_needed) { - log(DEBUG,"permission denied: %s %s",user->nick,command); - WriteServ(user->fd,"481 %s :Permission Denied- You do not have the required operator privilages",user->nick); - cmd_found = 1; - return; + if (!user->modes[cm->second->flags_needed-65]) + { + log(DEBUG,"permission denied: %s %s",user->nick,command); + WriteServ(user->fd,"481 %s :Permission Denied- You do not have the required operator privilages",user->nick); + cmd_found = 1; + return; + } } if ((cm->second->flags_needed) && (!user->HasPermission(xcommand))) { diff --git a/src/helperfuncs.cpp b/src/helperfuncs.cpp index 6250b6285..c190aff4e 100644 --- a/src/helperfuncs.cpp +++ b/src/helperfuncs.cpp @@ -966,7 +966,7 @@ void WriteOpers_NoFormat(const char* text) if (IS_LOCAL(a)) { - if (a->modebits & UM_SERVERNOTICE) + if (a->modes[UM_SERVERNOTICE]) { // send server notices to all with +s WriteServ(a->fd,"NOTICE %s :%s",a->nick,text); @@ -1121,7 +1121,7 @@ void WriteWallOps(userrec *source, bool local_only, char* text, ...) { userrec* t = (userrec*)(*i); - if ((IS_LOCAL(t)) && (t->modebits & UM_WALLOPS)) + if ((IS_LOCAL(t)) && (t->modes[UM_WALLOPS])) { WriteTo_NoFormat(source,t,formatbuffer); } @@ -1334,7 +1334,7 @@ void userlist(userrec *user,chanrec *c) for (CUList::iterator i = ulist->begin(); i != ulist->end(); i++) { - if ((!has_user) && (i->second->modebits & UM_INVISIBLE)) + if ((!has_user) && (i->second->modes[UM_INVISIBLE])) { /* * user is +i, and source not on the channel, does not show @@ -1385,7 +1385,7 @@ int usercount_i(chanrec *c) CUList *ulist= c->GetUsers(); for (CUList::iterator i = ulist->begin(); i != ulist->end(); i++) { - if (!(i->second->modebits & UM_INVISIBLE)) + if (!(i->second->modes[UM_INVISIBLE])) count++; } @@ -1499,7 +1499,7 @@ int usercount_invisible(void) for (user_hash::const_iterator i = clientlist.begin(); i != clientlist.end(); i++) { - if ((i->second->registered == 7) && (i->second->modebits & UM_INVISIBLE)) + if ((i->second->registered == 7) && (i->second->modes[UM_INVISIBLE])) c++; } diff --git a/src/message.cpp b/src/message.cpp index 28a11fda9..5106bffba 100644 --- a/src/message.cpp +++ b/src/message.cpp @@ -198,11 +198,11 @@ int c_count(userrec* u) } -bool hasumode(userrec* user, char mode) +bool hasumode(userrec* user, unsigned char mode) { if (user) { - return (strchr(user->modes,mode)>0); + return user->modes[mode-65]; } else return false; } @@ -422,7 +422,7 @@ std::string chlist(userrec *user,userrec* source) * If the channel is NOT private/secret AND the user is not invisible. * If the user is an oper, and the <options:operspywhois> option is set. */ - if ((source == user) || (*source->oper && Config->OperSpyWhois) || (((!rec->channel->modes[CM_PRIVATE]) && (!rec->channel->modes[CM_SECRET]) && !(user->modebits & UM_INVISIBLE)) || (rec->channel->HasUser(source)))) + if ((source == user) || (*source->oper && Config->OperSpyWhois) || (((!rec->channel->modes[CM_PRIVATE]) && (!rec->channel->modes[CM_SECRET]) && !(user->modes[UM_INVISIBLE])) || (rec->channel->HasUser(source)))) { list << cmode(user, rec->channel) << rec->channel->name << " "; } diff --git a/src/modules/extra/m_sqloper.cpp b/src/modules/extra/m_sqloper.cpp index 08ac72bcf..f39be098c 100644 --- a/src/modules/extra/m_sqloper.cpp +++ b/src/modules/extra/m_sqloper.cpp @@ -145,9 +145,9 @@ class ModuleSQLOper : public Module strlcpy(user->oper,rowresult->GetField("type").c_str(),NICKMAX-1); WriteOpers("*** %s (%s@%s) is now an IRC operator of type %s",user->nick,user->ident,user->host,rowresult->GetField("type").c_str()); WriteServ(user->fd,"381 %s :You are now an IRC operator of type %s",user->nick,rowresult->GetField("type").c_str()); - if(!strchr(user->modes,'o')) + if(user->modes[UM_OPERATOR]) { - strcat(user->modes,"o"); + user->modes[UM_OPERATOR] = 1; WriteServ(user->fd,"MODE %s :+o",user->nick); FOREACH_MOD(I_OnOper,OnOper(user,rowresult->GetField("type"))); AddOper(user); diff --git a/src/modules/m_botmode.cpp b/src/modules/m_botmode.cpp index 04204b42e..612eb3b9c 100644 --- a/src/modules/m_botmode.cpp +++ b/src/modules/m_botmode.cpp @@ -68,7 +68,7 @@ class ModuleBotMode : public Module virtual void OnWhois(userrec* src, userrec* dst) { - if (strchr(dst->modes,'B')) + if (dst->modes['B'-65]) { Srv->SendTo(NULL,src,"335 "+std::string(src->nick)+" "+std::string(dst->nick)+" :is a \2bot\2 on "+Srv->GetNetworkName()); } diff --git a/src/modules/m_cban.cpp b/src/modules/m_cban.cpp index 06284a964..fd6a92c22 100644 --- a/src/modules/m_cban.cpp +++ b/src/modules/m_cban.cpp @@ -164,7 +164,7 @@ class ModuleCBan : public Module /* check cbans in here, and apply as necessary. */ for(cbanlist::iterator iter = cbans.begin(); iter != cbans.end(); iter++) { - if(iter->chname == cname && !strchr(user->modes, 'o')) + if(iter->chname == cname && !user->modes[UM_OPERATOR]) { // Channel is banned. WriteServ(user->fd, "384 %s %s :Cannot join channel, CBANed (%s)", user->nick, cname, iter->reason.c_str()); diff --git a/src/modules/m_censor.cpp b/src/modules/m_censor.cpp index 6a5acb54c..8c8bfc001 100644 --- a/src/modules/m_censor.cpp +++ b/src/modules/m_censor.cpp @@ -119,12 +119,12 @@ class ModuleCensor : public Module if (target_type == TYPE_USER) { userrec* t = (userrec*)dest; - active = (strchr(t->modes,'G') > 0); + active = t->modes['G'-65]; } else if (target_type == TYPE_CHANNEL) { chanrec* t = (chanrec*)dest; - active = (t->IsModeSet('G')); + active = t->IsModeSet('G'); } if (active) diff --git a/src/modules/m_check.cpp b/src/modules/m_check.cpp index 3ab31ebbc..5e7b4847c 100644 --- a/src/modules/m_check.cpp +++ b/src/modules/m_check.cpp @@ -70,7 +70,7 @@ class cmd_check : public command_t Srv->SendTo(NULL, user, checkstr + " nuh " + targuser->GetFullHost()); Srv->SendTo(NULL, user, checkstr + " realnuh " + targuser->GetFullRealHost()); Srv->SendTo(NULL, user, checkstr + " realname " + targuser->fullname); - Srv->SendTo(NULL, user, checkstr + " modes +" + targuser->modes); + Srv->SendTo(NULL, user, checkstr + " modes +" + targuser->FormatModes()); Srv->SendTo(NULL, user, checkstr + " server " + targuser->server); if (targuser->awaymsg[0] != 0) { diff --git a/src/modules/m_helpop.cpp b/src/modules/m_helpop.cpp index b6c723ca7..9a7124dda 100644 --- a/src/modules/m_helpop.cpp +++ b/src/modules/m_helpop.cpp @@ -234,7 +234,7 @@ class ModuleHelpop : public Module virtual void OnWhois(userrec* src, userrec* dst) { - if (strchr(dst->modes,'h')) + if (dst->modes['h'-65]) { Srv->SendTo(NULL,src,"310 "+std::string(src->nick)+" "+std::string(dst->nick)+" :is available for help."); } diff --git a/src/modules/m_park.cpp b/src/modules/m_park.cpp index 7abe31baf..a5c62da19 100644 --- a/src/modules/m_park.cpp +++ b/src/modules/m_park.cpp @@ -161,11 +161,11 @@ class cmd_unpark : public command_t } } // remove all their old modes - WriteServ(user->fd,"MODE %s -%s",user->nick,user->modes); + WriteServ(user->fd,"MODE %s -%s",user->nick,user->FormatModes()); // now, map them to the parked user, while nobody can see :p Srv->PseudoToUser(user,unpark,"Unparked to "+std::string(parameters[0])); // set all their new modes - WriteServ(unpark->fd,"MODE %s +%s",unpark->nick,unpark->modes); + WriteServ(unpark->fd,"MODE %s +%s",unpark->nick,unpark->FormatModes()); // spool their away log to them WriteServ(unpark->fd,"NOTICE %s :*** You are now unparked. You have successfully taken back the nickname and privilages of %s.",unpark->nick,unpark->nick); for (awaylog::iterator i = awy->begin(); i != awy->end(); i++) diff --git a/src/modules/m_services.cpp b/src/modules/m_services.cpp index 4d5183841..c868eefef 100644 --- a/src/modules/m_services.cpp +++ b/src/modules/m_services.cpp @@ -54,7 +54,7 @@ class ModuleServices : public Module /* <- :stitch.chatspike.net 307 w00t w00t :is a registered nick */ virtual void OnWhois(userrec* source, userrec* dest) { - if (strchr(dest->modes, 'r')) + if (dest->modes['r'-65]) { /* user is registered */ WriteServ(source->fd, "307 %s %s :is a registered nick", source->nick, dest->nick); @@ -69,7 +69,7 @@ class ModuleServices : public Module virtual void OnUserPostNick(userrec* user, const std::string &oldnick) { /* On nickchange, if they have +r, remove it */ - if (strchr(user->modes,'r')) + if (user->modes['r'-65]) { char* modechange[2]; modechange[0] = user->nick; @@ -133,7 +133,7 @@ class ModuleServices : public Module if (target_type == TYPE_CHANNEL) { chanrec* c = (chanrec*)dest; - if ((c->IsModeSet('M')) && (!strchr(user->modes,'r'))) + if ((c->IsModeSet('M')) && (!user->modes['r'-65])) { if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server)) || (!strcmp(user->server,""))) { @@ -148,7 +148,7 @@ class ModuleServices : public Module if (target_type == TYPE_USER) { userrec* u = (userrec*)dest; - if ((strchr(u->modes,'R')) && (!strchr(user->modes,'r'))) + if ((u->modes['R'-65]) && (user->modes['r'-65])) { if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server))) { @@ -174,7 +174,7 @@ class ModuleServices : public Module { if (chan->IsModeSet('R')) { - if (!strchr(user->modes,'r')) + if (user->modes['r'-65]) { if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server))) { diff --git a/src/modules/m_services_account.cpp b/src/modules/m_services_account.cpp index 62e9baf17..c27e103b7 100644 --- a/src/modules/m_services_account.cpp +++ b/src/modules/m_services_account.cpp @@ -105,7 +105,7 @@ class ModuleServicesAccount : public Module { userrec* u = (userrec*)dest; - if ((strchr(u->modes,'R')) && (!account)) + if ((u->modes['R'-65]) && (!account)) { if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server))) { diff --git a/src/modules/m_showwhois.cpp b/src/modules/m_showwhois.cpp index dddd29406..519b13352 100644 --- a/src/modules/m_showwhois.cpp +++ b/src/modules/m_showwhois.cpp @@ -48,7 +48,7 @@ class ModuleShowwhois : public Module virtual void OnWhois(userrec* source, userrec* dest) { - if((strchr(dest->modes,'W')) && (source != dest)) + if ((dest->modes['W'-65]) && (source != dest)) { WriteServ(dest->fd,"NOTICE %s :*** %s (%s@%s) did a /whois on you.",dest->nick,source->nick,source->ident,source->host); } diff --git a/src/modules/m_spanningtree.cpp b/src/modules/m_spanningtree.cpp index 841206b8f..076241dea 100644 --- a/src/modules/m_spanningtree.cpp +++ b/src/modules/m_spanningtree.cpp @@ -1176,24 +1176,10 @@ class TreeSocket : public InspSocket strlcpy(clientlist[tempnick]->fullname, params[7].c_str(),MAXGECOS); clientlist[tempnick]->registered = 7; clientlist[tempnick]->signon = age; - strlcpy(clientlist[tempnick]->modes, params[5].c_str(),53); - for (char *v = clientlist[tempnick]->modes; *v; v++) + for (std::string::iterator v = params[5].begin(); v != params[5].end(); v++) { - switch (*v) - { - case 'i': - clientlist[tempnick]->modebits |= UM_INVISIBLE; - break; - case 'w': - clientlist[tempnick]->modebits |= UM_WALLOPS; - break; - case 's': - clientlist[tempnick]->modebits |= UM_SERVERNOTICE; - break; - default: - break; - } + clientlist[tempnick]->modes[(*v)-65] = 1; } inet_aton(params[6].c_str(),&clientlist[tempnick]->ip4); @@ -1391,7 +1377,7 @@ class TreeSocket : public InspSocket { if (u->second->registered == 7) { - snprintf(data,MAXBUF,":%s NICK %lu %s %s %s %s +%s %s :%s",u->second->server,(unsigned long)u->second->age,u->second->nick,u->second->host,u->second->dhost,u->second->ident,u->second->modes,inet_ntoa(u->second->ip4),u->second->fullname); + snprintf(data,MAXBUF,":%s NICK %lu %s %s %s %s +%s %s :%s",u->second->server,(unsigned long)u->second->age,u->second->nick,u->second->host,u->second->dhost,u->second->ident,u->second->FormatModes(),inet_ntoa(u->second->ip4),u->second->fullname); this->WriteLine(data); if (*u->second->oper) { @@ -1555,11 +1541,8 @@ class TreeSocket : public InspSocket userrec* u = Srv->FindNick(prefix); if (u) { + u->modes[UM_OPERATOR] = 1; strlcpy(u->oper,opertype.c_str(),NICKMAX-1); - if (!strchr(u->modes,'o')) - { - strcat(u->modes,"o"); - } DoOneToAllButSender(u->nick,"OPERTYPE",params,u->server); } return true; @@ -3667,7 +3650,7 @@ class ModuleSpanningTree : public Module params.push_back(user->host); params.push_back(user->dhost); params.push_back(user->ident); - params.push_back("+"+std::string(user->modes)); + params.push_back("+"+std::string(user->FormatModes())); params.push_back((char*)inet_ntoa(user->ip4)); params.push_back(":"+std::string(user->fullname)); DoOneToMany(Srv->GetServerName(),"NICK",params); diff --git a/src/modules/m_stripcolor.cpp b/src/modules/m_stripcolor.cpp index 0875399b8..1b8f8c72d 100644 --- a/src/modules/m_stripcolor.cpp +++ b/src/modules/m_stripcolor.cpp @@ -128,7 +128,7 @@ class ModuleStripColor : public Module if (target_type == TYPE_USER) { userrec* t = (userrec*)dest; - active = (strchr(t->modes,'S') > 0); + active = t->modes['S'-65]; } else if (target_type == TYPE_CHANNEL) { diff --git a/src/users.cpp b/src/users.cpp index 87dfca4ab..78409dc6f 100644 --- a/src/users.cpp +++ b/src/users.cpp @@ -113,17 +113,18 @@ bool DoneClassesAndTypes(const char* tag) userrec::userrec() { // the PROPER way to do it, AVOID bzero at *ALL* costs - *password = *nick = *ident = *host = *dhost = *fullname = *modes = *awaymsg = *oper = 0; + *password = *nick = *ident = *host = *dhost = *fullname = *awaymsg = *oper = 0; server = (char*)FindServerNamePtr(Config->ServerName); reset_due = TIME; lines_in = fd = lastping = signon = idle_lastmsg = nping = registered = 0; - modebits = timeout = flood = port = bytes_in = bytes_out = cmds_in = cmds_out = 0; + timeout = flood = port = bytes_in = bytes_out = cmds_in = cmds_out = 0; haspassed = dns_done = false; recvq = ""; sendq = ""; chans.clear(); invites.clear(); chans.resize(MAXCHANS); + memset(modes,0,sizeof(modes)); for (unsigned int n = 0; n < MAXCHANS; n++) { |