-
-static unsigned int* getModeOptions(char mode) {
- unsigned int *cmode;
- for (cmode = valid_modes; cmode[1]; cmode += 3) {
- if(cmode[1] == mode)
- return cmode;
- }
- return NULL;
-}
-
-int isModeSet(struct ChanNode* chan, char modeChar) {
- unsigned int *modeOpt = getModeOptions(modeChar);
- return (chan->modes & modeOpt[0]);
-}
-
-void* getModeValue(struct ChanNode* chan, char modeChar) {
- #define MODE_VALUE_INDEX (modeOpt[2] & CHANNEL_MODE_VALUE_INDEX_MASK) >> CHANNEL_MODE_VALUE_INDEX_SHIFT
- unsigned int *modeOpt = getModeOptions(modeChar);
- if((modeOpt[2] & CHANNEL_MODE_VALUE) == CHANNEL_MODE_VALUE_STRING)
- return chan->mode_str_args[MODE_VALUE_INDEX];
- if((modeOpt[2] & CHANNEL_MODE_VALUE) == CHANNEL_MODE_VALUE_INTEGER)
- return &chan->mode_int_args[MODE_VALUE_INDEX];
- return NULL;
- #undef MODE_VALUE_INDEX
-}
-
-static void parseModesUserPriv(struct ChanNode* chan, unsigned char flag, int add, char *nick) {
- struct UserNode *user = getUserByNick(nick);
- if(user == NULL) return;
- struct ChanUser *chanuser = getChanUser(user, chan);
- if(chanuser == NULL) return;
- if(add)
- chanuser->flags |= flag;
- else
- chanuser->flags &= ~flag;
-}
-
-static void parseModesBan(struct ChanNode* chan, int add, char *mask) {
- //to be continued...
-}
-
-void parseModes(struct ChanNode* chan, char *modeStr, char **argv, int argc) {
- int i, argpos = 0, add = 1;
- #define MODE_TYPE (modeOpt[2] & CHANNEL_MODE_TYPE)
- #define MODE_VALUE (modeOpt[2] & CHANNEL_MODE_VALUE)
- #define MODE_VALUE_INDEX (modeOpt[2] & CHANNEL_MODE_VALUE_INDEX_MASK) >> CHANNEL_MODE_VALUE_INDEX_SHIFT
- unsigned int *modeOpt;
- for(i = 0; i < strlen(modeStr); i++) {
- if(modeStr[i] == '+') {
- add = 1;
- continue;
- }
- if(modeStr[i] == '-') {
- add = 0;
- continue;
- }
- modeOpt = getModeOptions(modeStr[i]);
- if(!modeOpt) continue; // unknown mode?
- if(MODE_TYPE == CHANNEL_MODE_TYPE_A) {
- if(argpos == argc) continue;
- //special mode ;)
- switch(modeStr[i]) {
- case 'o':
- parseModesUserPriv(chan, CHANUSERFLAG_OPPED, add, argv[argpos]);
- break;
- case 'v':
- parseModesUserPriv(chan, CHANUSERFLAG_VOICED, add, argv[argpos]);
- break;
- case 'b':
- parseModesBan(chan, add, argv[argpos]);
- break;
- default:
- //we have an unknown TYPE_A mode???
- break;
- }
- argpos++;
- continue;
- }
- if(add) {
- if(MODE_TYPE != CHANNEL_MODE_TYPE_D) { //all other types take parameters when set
- if(argpos == argc) continue;
- if(MODE_VALUE == CHANNEL_MODE_VALUE_STRING) {
- if(chan->mode_str_args[MODE_VALUE_INDEX])
- free(chan->mode_str_args[MODE_VALUE_INDEX]);
- chan->mode_str_args[MODE_VALUE_INDEX] = strdup(argv[argpos++]);
- } else if(MODE_VALUE == CHANNEL_MODE_VALUE_INTEGER)
- chan->mode_int_args[MODE_VALUE_INDEX] = atoi(argv[argpos++]);
- else
- argpos++; //we simply don't know what to do with the argument...
- }
- chan->modes |= modeOpt[0];
- } else {
- chan->modes &= ~modeOpt[0];
- if(MODE_TYPE == CHANNEL_MODE_TYPE_B) {
- if(argpos == argc) continue;
- if(MODE_VALUE == CHANNEL_MODE_VALUE_STRING) {
- free(chan->mode_str_args[MODE_VALUE_INDEX]);
- chan->mode_str_args[MODE_VALUE_INDEX] = NULL;
- } else if(MODE_VALUE == CHANNEL_MODE_VALUE_INTEGER)
- chan->mode_int_args[MODE_VALUE_INDEX] = 0;
- argpos++; //we don't need the argument when unsetting a mode...
- }
- }
- }
- #undef MODE_TYPE
- #undef MODE_VALUE
- #undef MODE_VALUE_INDEX
-}
-
-void getModeString(struct ChanNode* chan, char *modesStr) {
- #define MODE_TYPE (mode[2] & CHANNEL_MODE_TYPE)
- #define MODE_VALUE (mode[2] & CHANNEL_MODE_VALUE)
- #define MODE_VALUE_INDEX (mode[2] & CHANNEL_MODE_VALUE_INDEX_MASK) >> CHANNEL_MODE_VALUE_INDEX_SHIFT
- char paramStr[MAXLEN];
- modesStr[0] = '+';
- unsigned int *mode;
- int modePos = 1;
- int paramPos = 0;
- for (mode = valid_modes; mode[1]; mode += 3) {
- if(chan->modes & mode[0]) {
- modesStr[modePos++] = (char) mode[1];
- if(MODE_TYPE != CHANNEL_MODE_TYPE_D) {
- if(MODE_VALUE == CHANNEL_MODE_VALUE_STRING)
- paramPos += sprintf(paramStr + paramPos, " %s", chan->mode_str_args[MODE_VALUE_INDEX]);
- else if(MODE_VALUE == CHANNEL_MODE_VALUE_INTEGER)
- paramPos += sprintf(paramStr + paramPos, " %d", chan->mode_int_args[MODE_VALUE_INDEX]);
- }
- }
- }
- paramStr[paramPos] = '\0';
- strcpy(modesStr + modePos, paramStr);
- #undef MODE_TYPE
- #undef MODE_VALUE
- #undef MODE_VALUE_INDEX
-}
-