bool KUser::CheckUser(unsigned long ip,unsigned gid)
{
	KUser_int_map::iterator it;
	m_lock.Lock();
	it=m_user.find(ip);
	if(it!=m_user.end()){
		if(gid==ALLUSER||gid==(*it).second.user_id){
	//		printf("gid==0 or gid == loginid\n");
			goto done;
		}
		for(int i=0;i<(*it).second.gids->size();i++){
			if(gid==(*it).second.gids->operator[](i)){

	//			printf("loginid in group gid.\n");
				goto done;
			}
		}
	}
	m_lock.Unlock();
	return false;
done:
	(*it).second.last_active_time=time(NULL);
	m_lock.Unlock();
	return true;
}
bool KUser::CheckLogin(const char *user)
{
	KUser_int_map::iterator it;
	m_lock.Lock();
	for(it=m_user.begin();it!=m_user.end();it++){
		if((*it).second.user->user==user){
			m_lock.Unlock();
			return true;
		}
	}
	m_lock.Unlock();
	return false;
}
void KUser::SaveAll()
{	

	unsigned stay_time=0;
	KUser_int_map::iterator it;
	int now_time=time(NULL);
	m_lock.Lock();
	for(it=m_user.begin();it!=m_user.end();it++){
		(*it).second.user->total_time+=now_time-(*it).second.login_time;
	}
	m_lock.Unlock();	
	Save();
}
std::string KUser::ListLoginUser()
{
	stringstream s;
	int now_time=time(NULL);
//	std::vector<std::string> user_list;
	s << "<table><tr><td></td><td>user</td><td>from</td><td>stay time(sec)</td><td>inactive time(sec)</td></tr>\n";
	KUser_int_map::iterator it;
	m_lock.Lock();
	for(it=m_user.begin();it!=m_user.end();it++){
		s << "<tr><td><a href=/killloginuser?user="******">kill</a></td><td>" << (*it).second.user->user << "</td><td>" << make_ip((*it).first) << "</td><td>" << (now_time-(*it).second.login_time) << "</td><td>" << (now_time-(*it).second.last_active_time) << "</td></tr>\n";
	}
//		user_list.push_back((*it).second.user);
	m_lock.Unlock();
	s << "</table>";
	return s.str();
}
bool KUser::ForceLogout(const char *user,bool use_lock)
{
	KUser_int_map::iterator it;
	if(use_lock)
		m_lock.Lock();
	for(it=m_user.begin();it!=m_user.end();it++){
		if((*it).second.user->user==user){
			(*it).second.user->state=0;
			klog(RUN_LOG,"Force logou user %s success\n",(*it).second.user->user.c_str());
			m_user.erase(it);
			m_lock.Unlock();
			return true;
		}
	}
	if(use_lock)
		m_lock.Unlock();
	return false;
}
int KUser::Logout(unsigned long ip)
{
	unsigned stay_time=0;
	KUser_int_map::iterator it;
	m_lock.Lock();
	it=m_user.find(ip);
	if(it==m_user.end()){
		m_lock.Unlock();
		return stay_time;
	}
	stay_time=time(NULL)-(*it).second.login_time;
	//m_user.total_time+=stay_time;
	(*it).second.user->total_time+=stay_time;
	(*it).second.user->state=0;//set the user logout
	klog(RUN_LOG,"user %s logout success\n",(*it).second.user->user.c_str());
	m_user.erase(it);
	m_lock.Unlock();	
	return stay_time;
}
bool KUser::Login(unsigned long ip,const char *user)
{
	UserInfo m_userinfo;
	if(!LoadUserInfo(user,m_userinfo))
		return false;
	LoginUserInfo tmpuser;
	stringmap::iterator it2;
	KUser_int_map::iterator it;
	tmpuser.login_time=time(NULL);
	tmpuser.last_active_time=tmpuser.login_time;
	//tmpuser.user=user;
	m_root_lock.Lock();
	it2=m_all_user.find(user);
	if(it2==m_all_user.end()){
		m_root_lock.Unlock();
		return false;
	}
	(*it2).second->last_ip=ip;
	(*it2).second->state=1;//set the user login
	(*it2).second->last_time=tmpuser.login_time;
	tmpuser.user=(*it2).second;
	tmpuser.user_id=(*it2).second->uid;
	tmpuser.gids=&(*it2).second->gids;
	m_root_lock.Unlock();
	if(tmpuser.user_id==0){
		klog(ERR_LOG,"user %s user_id is 0,It may be a bug in %s:%d\n",user,__FILE__,__LINE__);
		return false;
	}
	m_lock.Lock();
	it=m_user.find(ip);
	if(it!=m_user.end())
		goto err;
	ForceLogout(user,false);
	m_user[ip]=tmpuser;
	m_lock.Unlock();
	char ips[18];
	make_ip(ip,ips);
	klog(RUN_LOG,"user %s(%d) login from %s success\n",user,tmpuser.user_id,ips);
	return true;
err:
	m_lock.Unlock();
	return false;
}
unsigned KUser::CheckLogin(unsigned long ip,LoginUserInfo *user_info)
{	
	unsigned uid=0;
	KUser_int_map::iterator it;
	m_lock.Lock();
	it=m_user.find(ip);
	if(it!=m_user.end()){
		uid=(*it).second.user_id;
		if(user_info!=NULL){
			//memcpy(user_info,&(*it).second,sizeof(LoginUserInfo));
			user_info->user_id=uid;
			user_info->user=(*it).second.user;
			user_info->login_time=(*it).second.login_time;
			//user_info->last_ip=(*it).second.last_ip;
		}
	}
	m_lock.Unlock();
	return uid;


}
void KUser::FlushLoginUser()
{
	if(conf.user_time_out<=0)
		return;
	int now_time=time(NULL);
	KUser_int_map::iterator it;
	m_lock.Lock();
	for(it=m_user.begin();it!=m_user.end();){
		if(now_time-(*it).second.last_active_time>conf.user_time_out){
	#ifndef _WIN32
			(*it).second.user->state=0;
			m_user.erase(it);
			it++;
	#else
			it=m_user.erase(it);
	#endif
		}else{
			it++;
		}
	}
	m_lock.Unlock();
}
void KUser::UpdateSendRecvSize(unsigned long ip,int send_size,int recv_size,unsigned uid)
{
	assert(send_size>=0 && recv_size>=0);
	KUser_int_map::iterator it;
	if(uid>STARTUID){
		map<unsigned,UserInfo *>::iterator it2;
		m_root_lock.Lock();
		it2=m_all_user2.find(uid);
		if(it2!=m_all_user2.end()){
			(*it2).second->send_size+=send_size;
			(*it2).second->recv_size+=recv_size;
		}
		m_root_lock.Unlock();
		return;
	}
	m_lock.Lock();
	it=m_user.find(ip);
	if(it!=m_user.end()){
		(*it).second.user->send_size+=send_size;
		(*it).second.user->recv_size+=recv_size;
	}
	m_lock.Unlock();
}