使用aio写socket通信程序
发送端代码[code]
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include <netinet/in.h> /*socket address struct*/
#include <arpa/inet.h> /*host to network convertion*/
#include <sys/socket.h>
#include <signal.h>
#define MAX_TRANSPORT_LENTH 512
int main()
{
struct sockaddr_in addr;
memset(&addr,0,sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = inet_addr("127.0.0.1");
addr.sin_port = htons(50001);
int sock;
sock = socket(AF_INET,SOCK_DGRAM,0);
if(sock == -1)
{
perror("Create socket failed");
exit(-1);
}
int ret;
ret = connect(sock,(struct sockaddr *)&addr,sizeof(addr));
if(ret == -1)
{
perror("Connect socket failed");
exit(-1);
}
while(1)
{
printf("Will send messge to server\n");
write(sock,"Some unknown infomation\n",MAX_TRANSPORT_LENTH);
sleep(1);
}
}
[/code]
发送端同上篇帖子相比,没啥区别。
主要不同的在于接收端,因为是采用了aio,所以很有些不同
接收端代码
[code]
#include <aio.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include <netinet/in.h> /*socket address struct*/
#include <arpa/inet.h> /*host to network convertion*/
#include <sys/socket.h>
#include <sys/types.h>
#include <signal.h>
//#include <sys/ioctl.h>
#define MAX_TRANSPORT_LENTH 512
#define MAX_LIST 5
void sig_handler(int signo, siginfo_t *info, void *context )
{
int ret;
struct aiocb *req;
/* Ensure it's our signal */
if (info->si_signo == SIGIO) {
req = (struct aiocb *)info->si_value.sival_ptr;
if (aio_error( req ) == 0) {
ret = aio_return( req );
(char*)(req->aio_buf+ret) == '\0';
puts(req->aio_buf);
}
}
return;
}
int main()
{
int skt_fd,ret;
struct aiocb my_aiocb;
struct sigaction sig_act;
struct sockaddr_in addr;
memset(&addr,0,sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = INADDR_ANY;
addr.sin_port = htons(50001);
skt_fd = socket(AF_INET, SOCK_DGRAM, 0);
if(skt_fd == -1)
{
perror("Create socket failed");
exit(-1);
}
ret = bind(skt_fd,(struct sockaddr *)&addr,sizeof(addr));
if(-1 == ret)
{
perror("Bind socket failed");
exit(-1);
}
memset(&my_aiocb,0,sizeof(my_aiocb));
my_aiocb.aio_buf = malloc(MAX_TRANSPORT_LENTH+1);
if (!my_aiocb.aio_buf)
perror("malloc");
my_aiocb.aio_fildes = skt_fd;
my_aiocb.aio_nbytes = MAX_TRANSPORT_LENTH;
my_aiocb.aio_offset = 0;
my_aiocb.aio_sigevent.sigev_notify = SIGEV_SIGNAL;
my_aiocb.aio_sigevent.sigev_signo = SIGIO;
my_aiocb.aio_sigevent.sigev_value.sival_ptr = &my_aiocb;
sigemptyset(&sig_act.sa_mask);
sig_act.sa_flags = SA_SIGINFO;
sig_act.sa_sigaction = sig_handler;
const struct aiocb *cblist[MAX_LIST] ={&my_aiocb,NULL,NULL,NULL,NULL};
sigaction( SIGIO, &sig_act, NULL );
ret = aio_read( &my_aiocb );
//程序挂起直到等到某个信号
while ( aio_suspend( cblist, MAX_LIST, NULL ) == 0)
{
ret = aio_read( &my_aiocb );
};
puts("Interrupted finish.");
close(skt_fd);
}
[/code]
在这里,如果用my_aiocb.aio_sigevent.sigev_notify = SIGEV_THREAD;
则可以指定一个回调函数来完成读取数据的操作,这种方法还是希望对此文感兴趣的伙伴加以完善吧。 SIGIO不是AIO吧,只能算是非诸塞同步IO吧?
页:
[1]