rob@76: /* rob@76: OSCgroups -- open sound control groupcasting infrastructure rob@76: Copyright (C) 2005 Ross Bencina rob@76: rob@76: This program is free software; you can redistribute it and/or rob@76: modify it under the terms of the GNU General Public License rob@76: as published by the Free Software Foundation; either version 2 rob@76: of the License, or (at your option) any later version. rob@76: rob@76: This program is distributed in the hope that it will be useful, rob@76: but WITHOUT ANY WARRANTY; without even the implied warranty of rob@76: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the rob@76: GNU General Public License for more details. rob@76: rob@76: You should have received a copy of the GNU General Public License rob@76: along with this program; if not, write to the Free Software rob@76: Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. rob@76: */ rob@76: rob@76: #ifndef INCLUDED_GROUPSERVER_H rob@76: #define INCLUDED_GROUPSERVER_H rob@76: rob@76: // GroupServer.h/cpp implements user and group admission control using passwords rob@76: // Users live as long as they are sending alive messages more frequency rob@76: // than the timeout value. Groups live as long as they have members. rob@76: // Once Users and Groups are destroyed they can be reused with different rob@76: // passwords. rob@76: // This module has no dependence on the messaging protocol, although it does rob@76: // assume IPV4 addresses. rob@76: rob@76: rob@76: #include rob@76: #include rob@76: #include rob@76: #include rob@76: rob@76: #include "ip/IpEndpointName.h" rob@76: rob@76: class User; rob@76: class Group; rob@76: class GroupServer; rob@76: rob@76: rob@76: class User{ rob@76: friend class GroupServer; rob@76: rob@76: std::set groups_; rob@76: rob@76: public: rob@76: User( const char *userName, const char *userPassword ) rob@76: : name( userName ) rob@76: , password( userPassword ) {} rob@76: rob@76: std::string name; rob@76: std::string password; rob@76: rob@76: IpEndpointName privateEndpoint; rob@76: IpEndpointName publicEndpoint; rob@76: rob@76: std::time_t lastAliveMessageArrivalTime; rob@76: rob@76: unsigned long SecondsSinceLastAliveReceived( std::time_t currentTime ) rob@76: { return (unsigned long)std::difftime( currentTime, lastAliveMessageArrivalTime ); } rob@76: rob@76: bool IsMemberOf( Group *group ) const rob@76: { return groups_.count( group ) == 1; } rob@76: rob@76: typedef std::set::const_iterator const_group_iterator; rob@76: const_group_iterator groups_begin() const { return groups_.begin(); } rob@76: const_group_iterator groups_end() const { return groups_.end(); } rob@76: }; rob@76: rob@76: rob@76: class Group{ rob@76: friend class GroupServer; rob@76: rob@76: std::set users_; rob@76: rob@76: public: rob@76: Group( const char *groupName, const char *groupPassword ) rob@76: : name( groupName ) rob@76: , password( groupPassword ) {} rob@76: rob@76: std::string name; rob@76: std::string password; rob@76: rob@76: typedef std::set::const_iterator const_user_iterator; rob@76: const_user_iterator users_begin() const { return users_.begin(); } rob@76: const_user_iterator users_end() const { return users_.end(); } rob@76: }; rob@76: rob@76: rob@76: class GroupServer{ rob@76: const int timeoutSeconds_; rob@76: const int maxUsers_; rob@76: const int maxGroups_; rob@76: rob@76: typedef std::map< std::string, User* > user_map; rob@76: typedef user_map::iterator user_iterator; rob@76: user_map users_; rob@76: int userCount_; rob@76: rob@76: typedef std::map< std::string, Group* > group_map; rob@76: typedef group_map::iterator group_iterator; rob@76: group_map groups_; rob@76: int groupCount_; rob@76: rob@76: User *CreateUser( const char *userName, const char *userPassword ); rob@76: rob@76: Group *CreateGroup( const char *groupName, const char *groupPassword ); rob@76: void AssociateUserWithGroup( User *user, Group* group ); rob@76: void RemoveUserReferenceFromGroup( User *user, Group* group ); rob@76: void SeparateUserFromGroup( User *user, Group* group ); rob@76: void SeparateUserFromAllGroups( User *user ); rob@76: rob@76: GroupServer(); // no default ctor rob@76: GroupServer( const GroupServer& ); // no copy ctor rob@76: GroupServer& operator=( const GroupServer& ); // no assignment operator rob@76: rob@76: public: rob@76: GroupServer( int timeoutSeconds, int maxUsers, int maxGroups ); rob@76: ~GroupServer(); rob@76: rob@76: enum UserStatus { rob@76: USER_STATUS_UNKNOWN, rob@76: USER_STATUS_OK, rob@76: USER_STATUS_WRONG_PASSWORD, rob@76: USER_STATUS_SERVER_LIMIT_REACHED rob@76: }; rob@76: rob@76: UserStatus UserAlive( const char *userName, const char *userPassword, rob@76: const IpEndpointName& privateEndpoint, rob@76: const IpEndpointName& publicEndpoint, rob@76: const char **groupNamesAndPasswords, rob@76: UserStatus *userGroupsStatus, int groupCount ); rob@76: rob@76: typedef user_map::const_iterator const_user_iterator; rob@76: const_user_iterator users_begin() const { return users_.begin(); } rob@76: const_user_iterator users_end() const { return users_.end(); } rob@76: User *FindUser( const char *userName ); rob@76: rob@76: typedef group_map::const_iterator const_group_iterator; rob@76: const_group_iterator groups_begin() const { return groups_.begin(); } rob@76: const_group_iterator groups_end() const { return groups_.end(); } rob@76: Group *FindGroup( const char *groupName ); rob@76: rob@76: void PurgeStaleUsers(); rob@76: }; rob@76: rob@76: rob@76: #endif /* INCLUDED_GROUPSERVER_H */