求助! RTT网络编程问题
以前我用ucos-ii+lwip, 结果BUG众多,不知如何解决,现在改用RTT后,运行得比较稳定了,RTT确实很不错!
现在我要实现服务器能被 多客户端同时访问, 我目前用的方法是BSD SOCKET的select机制,但是只要其中一个操作失败(现在是经常TCP读取超时)
便导致整个网络进程堵死,只有空闲程序在运行了...
我想请教下RTT能不能像LINUX那样fork出子进程,来实现同时处理多个客户端连接?
本人刚接触RTT,还望高手指点一二.. 大家帮忙看看我的select程序有无问题:
#include <lwip/sockets.h> /* 使用BSD Socket接口必须包含sockets.h这个头文件*/
#define MYPORT4000 //port we're listening on
int tcpserv(void)
{
fd_set master; //master file descriptor list
fd_set read_fds; //temp file descriptor list for select()
struct sockaddr_in myaddr; //server address
struct sockaddr_in remoteaddr; //client address
int fdmax; //maximum file descriptor number
int listener; //listening socket descriptor
int newfd; //newly accept()ed socket descriptor
char bufrecv;
char bufsend;
int nbytes;
int opt; //for setsocket()
int addrlen;
int i,j;
for(j = 0;j < 512; j++) {
bufsend = 't';
}
FD_ZERO(&master); //clear the master and temp sets
FD_ZERO(&read_fds);
//get the listener
listener = socket(AF_INET, SOCK_STREAM, 0);
//set the socket
setsockopt(listener, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(int));
//bind
myaddr.sin_family = AF_INET;
myaddr.sin_addr.s_addr = INADDR_ANY;
myaddr.sin_port = htons(MYPORT);
memset(&(myaddr.sin_zero), '\0', 8);
bind(listener, (struct sockaddr *)&myaddr, sizeof(myaddr));
//listen
listen(listener, 10);
//add the listener to the master set
FD_SET(listener, &master);
//keep track of the biggest file descriptor
fdmax = listener; //so far, it's this one
//main loop
for( ; ; ){
read_fds = master; //copy it
select(fdmax+1, &read_fds, NULL, NULL, NULL);
//run through the existing connections looking for data to read
for(i = 0; i <= fdmax; i++){
if(FD_ISSET(i, &read_fds)){ //we got one!!
if(i == listener){
//handler new connections
addrlen = sizeof(remoteaddr);
if((newfd = accept(listener, (struct sockaddr *)&remoteaddr, &addrlen)) == -1){
}else{
FD_SET(newfd, &master); //add to master set
if(newfd > fdmax){ //keep track of the maximum
fdmax = newfd;
}
}
}else{
//handle data from a client
nbytes = recv(i, bufrecv, sizeof(bufrecv), 0);
if(nbytes <= 0){
//got error or connection closed by client
closesocket(i); //bye!
FD_CLR(i, &master); //remove from master set
} else{
//send to client
send(i, bufsend, sizeof(bufsend), 0);
}
}
}
}
}
return 0;
} >> 以前我用ucos-ii+lwip, 结果BUG众多,不知如何解决
我怎么越看越像是托
你的问题反映到你的代码上,具体是什么地方出了问题?似乎没发现有超时的地方
这个吗:nbytes = recv(i, bufrecv, sizeof(bufrecv), 0);
fork的意思是创建一个进程,而进程与线程的区别体现在进程有独立的地址空间,而线程的地址空间是共享的。RT-Thread做为实时线程来说,当然整个地址空间都是共享的,所以不可能存在fork出一个进程的情况。
但反映到工作原理上,是可以创建出新的线程来服务客户端的,这样的坏处是比较占内存。 回复【2楼】ffxz
-----------------------------------------------------------------------
谢谢你的答复,
我不是托啊,
确实与我以前的UCOS-II工程比较, RTT工程代码量和内存占用都小了,而且稳定性高了.
我测试了你RTT0.2.4,echo了70多万次,除了有几个'打开TCP超时' 的错误外,没有啥异常,
不像我以前的工程,运行个几千次就发生 数据中止.... 0.2.4?!
不会你现在还在用0.2.4?换0.3.0正式版,0.2.4版本的lwip select铁定出问题。 不好意思,没说清楚..
我说的'TCP读取超时' 是我的客户端读取服务器数据时发生的.
服务器作用是:一接收到客户端发过来的任何数据,就会发给客户端512个字节,
不知为何服务器send函数没有成功发送数据到客户端? 回复【4楼】ffxz
-----------------------------------------------------------------------
是吗?那我赶紧换~ RTT0.3.0果然不错!
现在换成0.3.0版本后,3个客户端程序不停地访问服务器2个小时了,没有出现任何异常...明天接着测试..
值得一提的是:
我的硬件环境是AT91SAM7X256+DM9161, 用RTT0.3.0自带的网卡驱动文件会发生开机运行数秒钟后,网卡中断不响应了。 无法通信的情况!
正如ljt8015 在
http://www.ourdev.cn/bbs/bbs_content.jsp?bbs_sn=3910844&bbs_page_no=2&bbs_id=3066
中说的那样,后面我改用ljt8015所写的网卡驱动,就一切OK了!
还有就是AT91SAM7X256的EMAC有2种接口:MII和RMII,针对不同的接口,驱动程序会有所不同,
我觉得在网卡驱动中需要把这两种接口的驱动都写上去.
由于我用的是RMII接口,我修改了原驱动的三个地方:
sam7xether_init函数中:
AT91C_BASE_PIOB->PIO_PPUDR = (1<<16) | (1<<15);
改为
AT91C_BASE_PIOB->PIO_PPUDR = 1 << 15;
AT91C_BASE_EMAC->EMAC_USRIO= AT91C_EMAC_CLKEN;
改为
AT91C_BASE_EMAC->EMAC_USRIO= AT91C_EMAC_RMII | AT91C_EMAC_CLKEN;
linksetup函数中的以下指令注释掉:
// tout = read_phy(PHY_REG_BMCR);
// tout = read_phy(PHY_REG_BMCR);
// tout &= ~BMCR_ISOLATE;
// write_phy(PHY_REG_BMCR, tout); 哎,现在还是菜鸟的我,是纯粹的拿来主义者...
在这里感谢RTT团队,创造了这么好用的OS, 学习膜拜中.. >> 我的硬件环境是AT91SAM7X256+DM9161, 用RTT0.3.0自带的网卡驱动文件会发生开机运行数秒钟后,网卡中断不响应了。 无法通信的情况!
反馈给mbbill,^-^ 学习
页:
[1]