- 論壇徽章:
- 1
|
大概流程就是:main.c 主文件運(yùn)行后,接受客戶端連接,當(dāng)客戶端發(fā)相應(yīng)命令過來后,在tcp.c 文件中解析后,調(diào)用function.c文件中的處理函數(shù):Receive_Process()。
原來我的想法是,在function處理完成后,通過Receive_Process()函數(shù)再把結(jié)果返回,
[code=c]void Receive_Process(int conn_fd,unsigned char* buff_r,unsigned char* buff_w)[/code]
如果這樣的話,就沒這些問題了,處理的結(jié)果,我在tcp.c文件中,通過 “unsigned char* buff_w” 可以拿到,送給PC就完事了。
現(xiàn)在同事要求不這么干,即不通過Receive_Process()進(jìn)、出方式,把結(jié)果返回。而是要在fuction.c中(當(dāng)然也可能其他文件中可以調(diào)用發(fā)送函數(shù),把結(jié)果送給PC)把結(jié)果直接送給PC端...
(在另個(gè)帖子里可能沒描述清楚)
主文件:
主要就是網(wǎng)上找到一段代碼,簡(jiǎn)單調(diào)整了一下。
- #include "tcp.h"
- int main(int argc, char * argv[])
- {
- tcp_initialize();
- epoll_fd_tcp=create_epoll_tcp(MAX_EVENTS_TCP);
- while(1)
- {
- do_process_tcp_nowhile();
- sleep(1);
- }
- }
復(fù)制代碼 處理文件:function.c
- #include "function.h"
- void Receive_Process(int conn_fd,unsigned char* buff_r,unsigned char* buff_w)
- {
- unsigned char CmdKey;
- unsigned char length;
- int len,i;
- len = buff_r[1];
- CmdKey = buff_r[2];
- printf("packet len is : %02X\n",buff_r[1]);
- printf("cmdkey is : %02X\n",buff_r[2]);
- for(i=0;i<len;i++)
- buff_r[i]=buff_r[i+1];
- for(i=0;i<len;i++)
- printf("%02X ",buff_r[i]);
- printf("\n");
- switch(CmdKey)
- {
- case 0x02:
- //write_spi_arm_to_fpga_array(5,buff_r,buff_w);
- [color=#FF0000] // 根據(jù)命令,與FPGA交互后,將返回結(jié)果送給PC端,下面是模擬的數(shù)據(jù)。[/color]
- buff_w[0]=0x08;
- buff_w[1]=0x03;
- buff_w[2]=0x8c;
- buff_w[3]=0x00;
- buff_w[4]=0x00;
- //send to pc
- [color=#FF0000] tcp_send_data_to_pc(5 buff_w);[/color]
- // 無發(fā)完成發(fā)送任務(wù),這個(gè)函數(shù)只能在tcp.c文件中能正常,出了tcp.c文件就不行了。
- printf("CMD_GET_VERSION OK \n");
- break;
- default:
- break;
- }
- }
復(fù)制代碼 TCP文件: tcp.c
- #include "tcp.h"
- struct epoll_event events[MAX_EVENTS_TCP];// 事件監(jiān)聽隊(duì)列
- int server_sock_fd_tcp;// 服務(wù)器端套接字
- int client_sock_fd_tcp;// 客戶端套接字
- int nfds_tcp;// epoll監(jiān)聽事件發(fā)生的個(gè)數(shù)
- int len_recv_data_tcp;
- struct sockaddr_in host_addr_tcp; // 服務(wù)器網(wǎng)絡(luò)地址結(jié)構(gòu)體
- struct sockaddr_in remote_addr_tcp; // 客戶端網(wǎng)絡(luò)地址結(jié)構(gòu)體
- int sin_size;
- unsigned char send_data_buffer_size_tcp[BUFFER_SIZE_TCP]; // 數(shù)據(jù)傳送的緩沖區(qū)
- unsigned char retn_data_buffer_size_tcp[BUFFER_SIZE_TCP];
- int m=0;
- int len;
- //設(shè)置句柄為非阻塞方式
- int setnonblocking(int sockfd)
- {
- if (fcntl(sockfd, F_SETFL, fcntl(sockfd, F_GETFD, 0)|O_NONBLOCK) == -1)
- {
- return -1;
- }
- return 0;
- }
- int tcp_send_data_to_pc(int len,char* buffer)
- {
- printf("in while n == %d \n",n);
- send(events[n].data.fd,buffer,4,0);
- ev.events = EPOLLIN;
- ev.data.fd = events[n].data.fd;
- epoll_ctl(epoll_fd_tcp, EPOLL_CTL_MOD, ev.data.fd, &ev);
- }
- void tcp_initialize()
- {
- struct rlimit rt;
-
- /* 設(shè)置每個(gè)進(jìn)程允許打開的最大文件數(shù) */
- rt.rlim_max = rt.rlim_cur = 1024;
- if (setrlimit(RLIMIT_NOFILE, &rt) == -1)
- {
- perror("setrlimit");
- exit(1);
- }
- else
- {
- printf("setrlimit ok! \n");
- }
-
- // 創(chuàng)建服務(wù)器端套接字--IPv4協(xié)議,面向連接通信,TCP協(xié)議
- if((server_sock_fd_tcp=socket(PF_INET,SOCK_STREAM,0))<0)
- {
- perror("socket");
- //return 1;
- }
- else
- {
- printf("Tcp server socket ok...\n");
- }
-
- // 設(shè)置 socket屬性,端口可以重用
-
- int opt=SO_REUSEADDR;
- setsockopt(server_sock_fd_tcp,SOL_SOCKET,SO_REUSEADDR,&opt,sizeof(opt));
- setnonblocking(server_sock_fd_tcp);
-
- memset(&host_addr_tcp,0,sizeof(host_addr_tcp)); // 數(shù)據(jù)初始化--清零
- host_addr_tcp.sin_family=PF_INET; // 設(shè)置為IP通信
- host_addr_tcp.sin_addr.s_addr=inet_addr(HOST_IP_ADDRESS_TCP);// 服務(wù)器IP地址--允許連接到所有本地地址上
- host_addr_tcp.sin_port=htons(HOST_PORT_TCP); // 服務(wù)器端口號(hào)
-
- // 將套接字綁定到服務(wù)器的網(wǎng)絡(luò)地址上
- if (bind(server_sock_fd_tcp,(struct sockaddr *)&host_addr_tcp,sizeof(struct sockaddr))<0)
- {
- perror("bind");
- //return 1;
- }
- else
- {
- printf("Tcp server bind ok...\n");
- printf("IP : %s \n", inet_ntoa(host_addr_tcp.sin_addr));
- printf("port: %d \n",ntohs(host_addr_tcp.sin_port));
- }
- // 監(jiān)聽連接請(qǐng)求--監(jiān)聽隊(duì)列長(zhǎng)度為5
- listen(server_sock_fd_tcp,64);
- sin_size=sizeof(struct sockaddr_in);
-
- }
-
- // 創(chuàng)建一個(gè)epoll句柄
- int create_epoll_tcp(unsigned int event_num)
- {
- int epoll_fd;
- epoll_fd=epoll_create(event_num);
- if(epoll_fd==-1)
- {
- perror("epoll_create failed");
- }
- ev.events=EPOLLIN | EPOLLET;
- ev.data.fd=server_sock_fd_tcp;
- // 向epoll注冊(cè)server_sockfd監(jiān)聽事件
- if(epoll_ctl(epoll_fd,EPOLL_CTL_ADD,server_sock_fd_tcp,&ev)==-1)
- {
- perror("epll_ctl:server_sock_fd_tcp register failed");
- }
- else
- {
- printf("socket adding in epoll success! \n");
- }
- return epoll_fd;
- }
-
- void do_process_tcp_nowhile()
- {
- // 等待事件發(fā)生
- nfds_tcp=epoll_wait(epoll_fd_tcp,events,1024,-1);
- if(nfds_tcp==-1)
- {
- perror("start epoll_wait failed");
- //exit(EXIT_FAILURE);
- }
- else
- {
- printf(" epoll nfds_tcp = %d \n",nfds_tcp);
- }
-
- for(n=0;n<nfds_tcp;++n)
- {
- printf(" for loop epoll nfds_tcp = %d \n",nfds_tcp);
- // 客戶端有新的連接請(qǐng)求
- if(events[n].data.fd == server_sock_fd_tcp)
- {
- // 等待客戶端連接請(qǐng)求到達(dá)
- if((client_sock_fd_tcp=accept(server_sock_fd_tcp,(struct sockaddr *)&remote_addr_tcp,&sin_size))<0)
- {
- perror("accept client_sock_fd_tcp failed");
- exit(EXIT_FAILURE);
- }
- // 向epoll注冊(cè)client_sockfd監(jiān)聽事件
- setnonblocking(client_sock_fd_tcp);
- ev.events=EPOLLIN | EPOLLET;
- ev.data.fd=client_sock_fd_tcp;
- if(epoll_ctl(epoll_fd_tcp,EPOLL_CTL_ADD,client_sock_fd_tcp,&ev)==-1)
- {
- perror("epoll_ctl:client_sock_fd_tcp register failed");
- }
- printf("accept client %s\n",inet_ntoa(remote_addr_tcp.sin_addr));
- }
- else if(events[n].events & EPOLLIN)
- {
- // 客戶端有數(shù)據(jù)發(fā)送過來
- sprintf(send_data_buffer_size_tcp,"");
- //sin_size=sizeof(remote_addr_tcp);
-
- len_recv_data_tcp=recv(events[n].data.fd,send_data_buffer_size_tcp,BUFFER_SIZE_TCP,0);
- if(len_recv_data_tcp<=0)
- {
- printf("close id is : %d \n",events[n].data.fd);
- if(epoll_ctl(epoll_fd_tcp,EPOLL_CTL_DEL,events[n].data.fd,&ev)==0)
- {
- printf("delete ok \n");
- close(events[n].data.fd);
- }
- else
- {
- printf("delete error \n");
- }
- }
- else
- {//[color=#FF0000]處理PC來的命令包,,調(diào)用fuction.c文件中的 Receive_Process()函數(shù)[/color]
- Receive_Process(4,send_data_buffer_size_tcp,retn_data_buffer_size_tcp);
-
- ev.data.fd = events[n].data.fd;
- ev.events = EPOLLOUT|EPOLLET;
- epoll_ctl(epoll_fd_tcp, EPOLL_CTL_MOD, events[n].data.fd, &ev);
- }
- }
- else if(events[n].events & EPOLLOUT)//發(fā)送
- {
- tcp_send_data_to_pc(4,send_data_buffer_size_tcp); [color=#FF0000]//這個(gè)地方就正常 [/color]
- }
- }
-
- if(server_sock_fd_tcp>0)
- {
- printf("socket close \n");
- shutdown(server_sock_fd_tcp,SHUT_RDWR);
- close(server_sock_fd_tcp);
- }
-
- }
復(fù)制代碼 tcp.h頭文件
- #include <arpa/inet.h>
- #include <fcntl.h>
- #include <sys/epoll.h>
- #include <sys/time.h>
- #include <sys/resource.h>
- #define BUFFER_SIZE_TCP 40
- #define MAX_EVENTS_TCP 10
- #define HOST_IP_ADDRESS_TCP "192.168.1.200"
- #define HOST_PORT_TCP 4530
- int n;
- struct epoll_event ev;// epoll事件結(jié)構(gòu)體
- int epoll_fd_tcp;
- int tcp_send_data_to_pc(int len,char* buffer);
- void tcp_initialize();
- int create_epoll_tcp(unsigned int event_num);
- void do_process_tcp_nowhile();
復(fù)制代碼 |
|