// ChannelUserList.C -*- C++ -*- // Copyright (c) 1997, 1998 Etienne BERNARD // Copyright (C) 2002,2005,2008,2009 Clinton Ebadi // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation; either version 2 of the License, or // any later version. // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // You should have received a copy of the GNU General Public License // along with this program; if not, write to the Free Software // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA // 02110-1301, USA. #include "ChannelUserList.H" #include "User.H" #include "UserList.H" #include "UserListItem.H" #include "Utils.H" #include #include ChannelUserList::ChannelUserList (const std::string & cn) throw () : users_mutex (true), channel_name (cn) { } ChannelUserList::~ChannelUserList () throw () { BotLock destructor_lock (users_mutex); while (users.begin () != users.end ()) { del (users.begin()->nick); } } std::list::iterator ChannelUserList::get_user_i_ (const std::string &name) { BotLock get_lock (users_mutex); return std::find_if (users.begin (), users.end (), std::bind1st (user_equal_p, User(name, 0))); } void ChannelUserList::add_ (std::string name, std::string host, int mode, UserListItem* user_list_item, bool names) throw () { BotLock add_lock (users_mutex); del (name); if (user_list_item) { if (user_list_item->identified) { user_list_item->identified++; } else if (user_list_item->passwd == "") { user_list_item->identified = 1; } } Utils::push_sorted (users, names ? User (name, mode) : User (name, host, channel_name, mode, user_list_item), user_less_p); } void ChannelUserList::add (std::string name, std::string host, int mode, UserList* user_list, bool names) throw () { BotLock add_lock (users_mutex); name = Utils::to_lower (name); UserListItem *uli = names ? 0 : user_list->getUserListItem (name + "!" + host, channel_name); add_ (name, host, mode, uli, names); } void ChannelUserList::del (const std::string &name) throw () { BotLock del_lock (users_mutex); std::list::iterator found = get_user_i_ (name); if (found != users.end ()) { if (found->userListItem && found->userListItem->identified > 0) found->userListItem->identified--; users.erase (found); } } User ChannelUserList::get (const std::string & name) const throw (user_not_found) { BotLock get_lock (users_mutex); std::list::const_iterator pos = std::find_if (users.begin (), users.end (), std::bind1st (user_equal_p, User(name, 0))); if (pos != users.end ()) return *pos; else throw user_not_found (name); } void ChannelUserList::change_nickname (const std::string & old_name, std::string new_name) throw (user_not_found) { BotLock change_lock (users_mutex); User user = get (old_name); del (old_name); add_ (new_name, user.userhost, user.mode, user.userListItem, false); } void ChannelUserList::change_user_mode (const std::string &name, int flag, bool remove) throw () { BotLock change_lock (users_mutex); std::list::iterator user = get_user_i_ (name); if (user != users.end ()) { remove ? user->mode &= ~flag : user->mode |= flag; } } bool ChannelUserList::in_channel_p (const std::string &name) const throw () { try { get (name); } catch (user_not_found &) { return false; } return true; } void ChannelUserList::change_user_key (const std::string &name, const std::string &key) throw () { std::list::iterator user = get_user_i_ (name); if (user != users.end ()) user->userkey = key; } unsigned int ChannelUserList::user_count () const throw () { return users.size (); } unsigned int ChannelUserList::operator_count () const throw () { unsigned int count = 0; for (std::list::const_iterator user = users.begin (); user != users.end (); ++user) { if (user->mode & User::OP_MODE) count++; } return count; }