select函數中的坑(C語言)

最近寫了一個測試驅動的poll函數的應用程序,在應用層中調用select進行操作,設置好timeout之後,如果只對select()調用一次,就沒有問題。但一旦多次調用後,就變成只有第一次timeout有效,後面的都沒有效果了。

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <fcntl.h>
#include <stdio.h>
#include <poll.h>
#include <unistd.h>


int main(int argc , char ** argv)
{
	int i;
	int fd;
	int ret;
	int press_cnt[4];
	fd_set rfds;
	struct timeval time;
	
	time.tv_sec = 5; //5s
	
	fd = open("/dev/buttons", O_RDWR);  //打開設備
	if(fd<0)
	{
		printf("Can't open");
		return -1;
	}


	while(1)
	{
		FD_ZERO(&rfds);
		FD_SET(fd, &rfds);
		ret = select(fd + 1, &rfds, NULL, NULL, &time);
		if (!ret)
		{
			printf("time out\n");
		}
		else
		{
			read(fd, press_cnt, sizeof(press_cnt)); //讀取值到press_cnt緩存區,讀取長度sizeof(press_cnt)
			for(i = 0 ; i<sizeof(press_cnt)/sizeof(press_cnt[0]);i++)
			{
				if(press_cnt[i]) //如果按下次數不爲0,打印出來
					printf("K%d has been pressed %d times \n", i+1, press_cnt[i]);
			}
		}
		
	}
}

後來查看了select()源碼,發現它會把timeout更新爲0,所以每次調用select(), 都要重新對timeout進行賦值。

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <fcntl.h>
#include <stdio.h>
#include <poll.h>
#include <unistd.h>


int main(int argc , char ** argv)
{
	int i;
	int fd;
	int ret;
	int press_cnt[4];
	fd_set rfds;
	struct timeval time;
	
	//time.tv_sec = 5; //5s
	
	fd = open("/dev/buttons", O_RDWR);  //打開設備
	if(fd<0)
	{
		printf("Can't open");
		return -1;
	}


	while(1)
	{
		time.tv_sec = 5; //5s
		time.tv_usec = 0;//select函數會不斷修改timeout的值,所以每次循環都應該重新賦值[windows不受此影響]
		FD_ZERO(&rfds);
		FD_SET(fd, &rfds);
		ret = select(fd + 1, &rfds, NULL, NULL, &time);
		if (!ret)
		{
			printf("time out\n");
		}
		else
		{
			read(fd, press_cnt, sizeof(press_cnt)); //讀取值到press_cnt緩存區,讀取長度sizeof(press_cnt)
			for(i = 0 ; i<sizeof(press_cnt)/sizeof(press_cnt[0]);i++)
			{
				if(press_cnt[i]) //如果按下次數不爲0,打印出來
					printf("K%d has been pressed %d times \n", i+1, press_cnt[i]);
			}
		}
		
	}
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章