Exemplo n.º 1
0
void  free_peer_node(Peer *node)
{
	if(node == NULL)  return;
	if(node->bitmap.bitfield != NULL) {
		free(node->bitmap.bitfield);
		node->bitmap.bitfield = NULL;
	}
	if(node->in_buff != NULL) {
		free(node->in_buff); 
		node->in_buff = NULL;
	}
	if(node->out_msg != NULL) {
		free(node->out_msg);
		node->out_msg = NULL;
	}
	if(node->out_msg_copy != NULL) {
		free(node->out_msg_copy);
		node->out_msg_copy = NULL;
	}

	cancel_request_list(node);
	cancel_requested_list(node);

	// 释放完peer成员的内存后,再释放peer所占的内存
	free(node);
}
Exemplo n.º 2
0
// 找出当前下载速度最快的4个peer,将其unchoke
int select_unchoke_peer()
{
	Peer*  p;
	Peer*  now_fast[UNCHOKE_COUNT];
	Peer*  force_choke[UNCHOKE_COUNT];
	int    unchoke_socket[UNCHOKE_COUNT], choke_socket[UNCHOKE_COUNT];
	int    i, j, index = 0, len = UNCHOKE_COUNT;

	int have_not_unchoke[UNCHOKE_COUNT];
	//初始化变量
	for(i = 0; i < len; i++) {
		now_fast[i]       = NULL;
		force_choke[i]    = NULL;
		unchoke_socket[i] = -1;
		choke_socket[i]   = -1;
		
		have_not_unchoke[i]  = -1;
	}

	// 将那些在过去10秒已断(被剔出peer表)开连接而又处于unchoke队列中的peer清除出unchoke队列
	for(i = 0, j = 0; i < unchoke_peers.count; i++) {
		p = peer_head;
		while(p != NULL) {
			if(p == unchoke_peers.unchkpeer[i])  break;
			p = p->next;
		}
		if(p == NULL) //不在peer链表中,说明已经断开
		 { unchoke_peers.unchkpeer[i] = NULL; j++; }
	}
	
	if(j != 0) {
		unchoke_peers.count = unchoke_peers.count - j;//剩下非阻塞数组未断开的个数
		for(i = 0, j = 0; i < len; i++) {
			if(unchoke_peers.unchkpeer[i] != NULL) {
				force_choke[j] = unchoke_peers.unchkpeer[i];
				j++;
			}
		}
		for(i = 0; i < len; i++) {//有效的挪到数组前排
			unchoke_peers.unchkpeer[i] = force_choke[i];
			force_choke[i] = NULL;
		}
	}

	// unchoke队列中,将那些在过去10秒上传速度超过20KB/S而下载速度过小的peer强行阻塞
	// 注意:up_rate和down_rate的单位是B/S而不是KB/S
	for(i = 0, j = -1; i < unchoke_peers.count; i++) {
		if( (unchoke_peers.unchkpeer)[i]->up_rate > 50*1024 && //到底是50k还是20k?
			(unchoke_peers.unchkpeer)[i]->down_rate < 0.1*1024 ) {
			j++;
			force_choke[j] = unchoke_peers.unchkpeer[i];
		}
	}

	// 从当前所有Peer中选出下载速度最快的四个peer,存于now_fast中
	p = peer_head;
	while(p != NULL) {
		if(p->state==DATA && is_interested(bitmap,&(p->bitmap)) && is_seed(p)!=1) {//state?交换数据?
			// p不应该在force_choke数组中
			for(i = 0; i < len; i++) {
				if(p == force_choke[i]) 
					break;
			}
			if(i == len) {
				if( index < UNCHOKE_COUNT ) {
					now_fast[index] = p; 
					index++; 
				} else { //数组满了
					j = get_last_index(now_fast,UNCHOKE_COUNT); //找now_fast最慢的那个和这个比较
					if(p->down_rate >= now_fast[j]->down_rate) now_fast[j] = p;
				}
			}
		}
		p = p->next;
	}
/**************************以下一段需要改进**********************************/
/*
	// 假设now_fast中所有的peer都是要unchoke的,取出各自的socket
	for(i = 0; i < index; i++) {
		Peer*  q = now_fast[i];
		unchoke_socket[i] = q->socket;
	}

	// 假设unchoke_peers.unchkpeer中所有peer都是choke的,取出各自的socket
	for(i = 0; i < unchoke_peers.count; i++) {
		Peer*  q = (unchoke_peers.unchkpeer)[i];
		choke_socket[i] = q->socket;
	}

	// 如果now_fast某个元素已经存在于unchoke_peers.unchkpeer
	// 则没有必要进行choke或unckoke
	for(i = 0; i < index; i++) {
		if( is_in_unchoke_peers(now_fast[i]) == 1) {//在unchoke_peers.unchkpeer,不用阻塞
		//	for(j = 0; j < len; j++) { //index与len不一定对应=4//但循环是为什么
				Peer*  q = now_fast[i];
				if(q->socket == unchoke_socket[i])  unchoke_socket[i] = -1;
				if(q->socket == choke_socket[i])    choke_socket[i]   = -1;
		//	}
		}
	}

	// 更新当前unchoke的peer
	for(i = 0; i < index; i++) {
		(unchoke_peers.unchkpeer)[i] = now_fast[i];
	}
	unchoke_peers.count = index;

	// 状态变化后,要对peer的状态值重新赋值,并且创建choke、unchoke消息
	p = peer_head;
	while(p != NULL) {
		for(i = 0; i < len; i++) {
			if(unchoke_socket[i]==p->socket && unchoke_socket[i]!=-1) {
				p->am_choking = 0;//非阻塞
				create_chock_interested_msg(1,p);
			}
			if(choke_socket[i]==p->socket && unchoke_socket[i]!=-1) {
				p->am_choking = 1;
				cancel_requested_list(p);
				create_chock_interested_msg(0,p);
			}
		}
		p = p->next;
	}
*/
/*******************************改进后*************************/
	for (i = 0; i < unchoke_peers.count; i++) {
		p = (unchoke_peers.unchkpeer)[i];
		for (j = 0; j < index; j++) {
			if(p == now_fast[j]) {
				break;
			}
		}
		if(j == index) {//peer在非阻塞队列中,但不在刚选出的now_fast中,将它阻塞
			p->am_choking = 1;
			cancel_requested_list(p);
			create_chock_interested_msg(0,p);	
		}
		else {
			have_not_unchoke[j] = 1;//记下now_fast中不必unchoke的位置
		}
	}
	for(i = 0; i < index; i++) {
		if(have_not_unchoke[i] != 1) { //说明now_fast对应位置要unchoke
			now_fast[i]->am_choking = 0;//转入非阻塞状态
			create_chock_interested_msg(1,now_fast[i]);
		}
	}
	//更新unchoke_peers
	for(i = 0; i < index; i++) {
		(unchoke_peers.unchkpeer)[i] = now_fast[i];
	}
	unchoke_peers.count = index;

/*****************************改进结束**************************/
	for(i = 0; i < unchoke_peers.count; i++)
		printf("unchoke peer:%s \n",(unchoke_peers.unchkpeer)[i]->ip);
	printf("***********************************************\n");
	return 0;
}