Libevent 사용 예, 간단 함 에서 복잡 함 까지

전재 출처 를 밝 혀 주 십시오: http://blog.csdn.net/luotuo44/article/details/39670221
본 고 는 간단 함 에서 복잡 함 까지 Libevent 를 어떻게 사용 하 는 지 보 여 준다.또한 인터넷 의 많은 예 는 서버 쪽 만 있 고 본 고 는 클 라 이언 트 와 서버 쪽 에 모두 있 습 니 다.이렇게 많아
초급:
클 라 이언 트 코드:
#include
#include
#include
#include
#include
#include

#include
#include
#include

#include
#include




int tcp_connect_server(const char* server_ip, int port);


void cmd_msg_cb(int fd, short events, void* arg);
void socket_read_cb(int fd, short events, void *arg);

int main(int argc, char** argv)
{
  if( argc < 3 )
  {
    printf("please input 2 parameter
"
); return -1; } // IP 、 int sockfd = tcp_connect_server(argv[1], atoi(argv[2])); if( sockfd == -1) { perror("tcp_connect error "); return -1; } printf("connect to server successful
"
); struct event_base* base = event_base_new(); struct event *ev_sockfd = event_new(base, sockfd, EV_READ | EV_PERSIST, socket_read_cb, NULL); event_add(ev_sockfd, NULL); // struct event* ev_cmd = event_new(base, STDIN_FILENO, EV_READ | EV_PERSIST, cmd_msg_cb, (void*)&sockfd); event_add(ev_cmd, NULL); event_base_dispatch(base); printf("finished
"
); return 0; } void cmd_msg_cb(int fd, short events, void* arg) { char msg[1024]; int ret = read(fd, msg, sizeof(msg)); if( ret <= 0 ) { perror("read fail "); exit(1); } int sockfd = *((int*)arg); // // , write(sockfd, msg, ret); } void socket_read_cb(int fd, short events, void *arg) { char msg[1024]; // , int len = read(fd, msg, sizeof(msg)-1); if( len <= 0 ) { perror("read fail "); exit(1); } msg[len] = '\0'; printf("recv %s from server
"
, msg); } typedef struct sockaddr SA; int tcp_connect_server(const char* server_ip, int port) { int sockfd, status, save_errno; struct sockaddr_in server_addr; memset(&server_addr, 0, sizeof(server_addr) ); server_addr.sin_family = AF_INET; server_addr.sin_port = htons(port); status = inet_aton(server_ip, &server_addr.sin_addr); if( status == 0 ) //the server_ip is not valid value { errno = EINVAL; return -1; } sockfd = ::socket(PF_INET, SOCK_STREAM, 0); if( sockfd == -1 ) return sockfd; status = ::connect(sockfd, (SA*)&server_addr, sizeof(server_addr) ); if( status == -1 ) { save_errno = errno; ::close(sockfd); errno = save_errno; //the close may be error return -1; } evutil_make_socket_nonblocking(sockfd); return sockfd; }

서버 쪽 코드:
#include
#include
#include

#include
#include



void accept_cb(int fd, short events, void* arg);
void socket_read_cb(int fd, short events, void *arg);

int tcp_server_init(int port, int listen_num);

int main(int argc, char** argv)
{

  int listener = tcp_server_init(9999, 10);
  if( listener == -1 )
  {
    perror(" tcp_server_init error ");
    return -1;
  }

  struct event_base* base = event_base_new();

  //             
  struct event* ev_listen = event_new(base, listener, EV_READ | EV_PERSIST,
                    accept_cb, base);
  event_add(ev_listen, NULL);


  event_base_dispatch(base);

  return 0;
}



void accept_cb(int fd, short events, void* arg)
{
  evutil_socket_t sockfd;

  struct sockaddr_in client;
  socklen_t len;

  sockfd = ::accept(fd, (struct sockaddr*)&client, &len );
  evutil_make_socket_nonblocking(sockfd);

  printf("accept a client %d
"
, sockfd); struct event_base* base = (event_base*)arg; // event struct event *ev = event_new(NULL, -1, 0, NULL, NULL); // event event_assign(ev, base, sockfd, EV_READ | EV_PERSIST, socket_read_cb, (void*)ev); event_add(ev, NULL); } void socket_read_cb(int fd, short events, void *arg) { char msg[4096]; struct event *ev = (struct event*)arg; int len = read(fd, msg, sizeof(msg) - 1); if( len <= 0 ) { printf("some error happen when read
"
); close(event_get_fd(ev)); event_free(ev); return ; } msg[len] = '\0'; printf("recv the client msg: %s", msg); char reply_msg[4096] = "I have recvieced the msg: "; strcat(reply_msg + strlen(reply_msg), msg); write(fd, reply_msg, strlen(reply_msg) ); } typedef struct sockaddr SA; int tcp_server_init(int port, int listen_num) { int errno_save; evutil_socket_t listener; listener = ::socket(AF_INET, SOCK_STREAM, 0); if( listener == -1 ) return -1; // 。 socket bind evutil_make_listen_socket_reuseable(listener); struct sockaddr_in sin; sin.sin_family = AF_INET; sin.sin_addr.s_addr = 0; sin.sin_port = htons(port); if( ::bind(listener, (SA*)&sin, sizeof(sin)) < 0 ) goto error; if( ::listen(listener, listen_num) < 0) goto error; // , evutil_make_socket_nonblocking(listener); return listener; error: errno_save = errno; evutil_closesocket(listener); errno = errno_save; return -1; }

중간:
클 라 이언 트 코드:
#include
#include
#include
#include
#include
#include

#include
#include
#include

#include
#include
#include
#include




int tcp_connect_server(const char* server_ip, int port);


void cmd_msg_cb(int fd, short events, void* arg);
void server_msg_cb(struct bufferevent* bev, void* arg);
void event_cb(struct bufferevent *bev, short event, void *arg);

int main(int argc, char** argv)
{
  if( argc < 3 )
  {
    printf("please input 2 parameter
"
); return -1; } // IP 、 int sockfd = tcp_connect_server(argv[1], atoi(argv[2])); if( sockfd == -1) { perror("tcp_connect error "); return -1; } printf("connect to server successful
"
); struct event_base* base = event_base_new(); struct bufferevent* bev = bufferevent_socket_new(base, sockfd, BEV_OPT_CLOSE_ON_FREE); // struct event* ev_cmd = event_new(base, STDIN_FILENO, EV_READ | EV_PERSIST, cmd_msg_cb, (void*)bev); event_add(ev_cmd, NULL); // socket bufferevent_setcb(bev, server_msg_cb, NULL, event_cb, (void*)ev_cmd); bufferevent_enable(bev, EV_READ | EV_PERSIST); event_base_dispatch(base); printf("finished
"
); return 0; } void cmd_msg_cb(int fd, short events, void* arg) { char msg[1024]; int ret = read(fd, msg, sizeof(msg)); if( ret < 0 ) { perror("read fail "); exit(1); } struct bufferevent* bev = (struct bufferevent*)arg; // bufferevent_write(bev, msg, ret); } void server_msg_cb(struct bufferevent* bev, void* arg) { char msg[1024]; size_t len = bufferevent_read(bev, msg, sizeof(msg)); msg[len] = '\0'; printf("recv %s from server
"
, msg); } void event_cb(struct bufferevent *bev, short event, void *arg) { if (event & BEV_EVENT_EOF) printf("connection closed
"
); else if (event & BEV_EVENT_ERROR) printf("some other error
"
); // close free bufferevent_free(bev); struct event *ev = (struct event*)arg; // socket , event event_free(ev); } typedef struct sockaddr SA; int tcp_connect_server(const char* server_ip, int port) { int sockfd, status, save_errno; struct sockaddr_in server_addr; memset(&server_addr, 0, sizeof(server_addr) ); server_addr.sin_family = AF_INET; server_addr.sin_port = htons(port); status = inet_aton(server_ip, &server_addr.sin_addr); if( status == 0 ) //the server_ip is not valid value { errno = EINVAL; return -1; } sockfd = ::socket(PF_INET, SOCK_STREAM, 0); if( sockfd == -1 ) return sockfd; status = ::connect(sockfd, (SA*)&server_addr, sizeof(server_addr) ); if( status == -1 ) { save_errno = errno; ::close(sockfd); errno = save_errno; //the close may be error return -1; } evutil_make_socket_nonblocking(sockfd); return sockfd; }

서버 쪽 코드:
#include
#include
#include

#include
#include



void accept_cb(int fd, short events, void* arg);
void socket_read_cb(bufferevent* bev, void* arg);
void event_cb(struct bufferevent *bev, short event, void *arg);
int tcp_server_init(int port, int listen_num);

int main(int argc, char** argv)
{

  int listener = tcp_server_init(9999, 10);
  if( listener == -1 )
  {
    perror(" tcp_server_init error ");
    return -1;
  }

  struct event_base* base = event_base_new();

  //             
  struct event* ev_listen = event_new(base, listener, EV_READ | EV_PERSIST,
                    accept_cb, base);
  event_add(ev_listen, NULL);


  event_base_dispatch(base);
  event_base_free(base);


  return 0;
}



void accept_cb(int fd, short events, void* arg)
{
  evutil_socket_t sockfd;

  struct sockaddr_in client;
  socklen_t len;

  sockfd = ::accept(fd, (struct sockaddr*)&client, &len );
  evutil_make_socket_nonblocking(sockfd);

  printf("accept a client %d
"
, sockfd); struct event_base* base = (event_base*)arg; bufferevent* bev = bufferevent_socket_new(base, sockfd, BEV_OPT_CLOSE_ON_FREE); bufferevent_setcb(bev, socket_read_cb, NULL, event_cb, arg); bufferevent_enable(bev, EV_READ | EV_PERSIST); } void socket_read_cb(bufferevent* bev, void* arg) { char msg[4096]; size_t len = bufferevent_read(bev, msg, sizeof(msg)); msg[len] = '\0'; printf("recv the client msg: %s", msg); char reply_msg[4096] = "I have recvieced the msg: "; strcat(reply_msg + strlen(reply_msg), msg); bufferevent_write(bev, reply_msg, strlen(reply_msg)); } void event_cb(struct bufferevent *bev, short event, void *arg) { if (event & BEV_EVENT_EOF) printf("connection closed
"
); else if (event & BEV_EVENT_ERROR) printf("some other error
"
); // close free bufferevent_free(bev); } typedef struct sockaddr SA; int tcp_server_init(int port, int listen_num) { int errno_save; evutil_socket_t listener; listener = ::socket(AF_INET, SOCK_STREAM, 0); if( listener == -1 ) return -1; // 。 socket bind evutil_make_listen_socket_reuseable(listener); struct sockaddr_in sin; sin.sin_family = AF_INET; sin.sin_addr.s_addr = 0; sin.sin_port = htons(port); if( ::bind(listener, (SA*)&sin, sizeof(sin)) < 0 ) goto error; if( ::listen(listener, listen_num) < 0) goto error; // , evutil_make_socket_nonblocking(listener); return listener; error: errno_save = errno; evutil_closesocket(listener); errno = errno_save; return -1; }

고등:
클 라 이언 트 코드:
#include
#include
#include
#include
#include
#include

#include
#include
#include

#include
#include
#include
#include




int tcp_connect_server(const char* server_ip, int port);


void cmd_msg_cb(int fd, short events, void* arg);
void server_msg_cb(struct bufferevent* bev, void* arg);
void event_cb(struct bufferevent *bev, short event, void *arg);

int main(int argc, char** argv)
{
  if( argc < 3 )
  {
    //            IP  、   
    printf("please input 2 parameter
"
); return -1; } struct event_base *base = event_base_new(); struct bufferevent* bev = bufferevent_socket_new(base, -1, BEV_OPT_CLOSE_ON_FREE); // struct event* ev_cmd = event_new(base, STDIN_FILENO, EV_READ | EV_PERSIST, cmd_msg_cb, (void*)bev); event_add(ev_cmd, NULL); struct sockaddr_in server_addr; memset(&server_addr, 0, sizeof(server_addr) ); server_addr.sin_family = AF_INET; server_addr.sin_port = htons(atoi(argv[2])); inet_aton(argv[1], &server_addr.sin_addr); bufferevent_socket_connect(bev, (struct sockaddr *)&server_addr, sizeof(server_addr)); bufferevent_setcb(bev, server_msg_cb, NULL, event_cb, (void*)ev_cmd); bufferevent_enable(bev, EV_READ | EV_PERSIST); event_base_dispatch(base); printf("finished
"
); return 0; } void cmd_msg_cb(int fd, short events, void* arg) { char msg[1024]; int ret = read(fd, msg, sizeof(msg)); if( ret < 0 ) { perror("read fail "); exit(1); } struct bufferevent* bev = (struct bufferevent*)arg; // bufferevent_write(bev, msg, ret); } void server_msg_cb(struct bufferevent* bev, void* arg) { char msg[1024]; size_t len = bufferevent_read(bev, msg, sizeof(msg)); msg[len] = '\0'; printf("recv %s from server
"
, msg); } void event_cb(struct bufferevent *bev, short event, void *arg) { if (event & BEV_EVENT_EOF) printf("connection closed
"
); else if (event & BEV_EVENT_ERROR) printf("some other error
"
); else if( event & BEV_EVENT_CONNECTED) { printf("the client has connected to server
"
); return ; } // close free bufferevent_free(bev); struct event *ev = (struct event*)arg; event_free(ev); }

서버 쪽 코드:
#include
#include
#include

#include
#include

#include
#include
#include
#include


void listener_cb(evconnlistener *listener, evutil_socket_t fd,
         struct sockaddr *sock, int socklen, void *arg);

void socket_read_cb(bufferevent *bev, void *arg);
void socket_event_cb(bufferevent *bev, short events, void *arg);

int main()
{
  //evthread_use_pthreads();//enable threads

  struct sockaddr_in sin;
  memset(&sin, 0, sizeof(struct sockaddr_in));
  sin.sin_family = AF_INET;
  sin.sin_port = htons(9999);

  event_base *base = event_base_new();
  evconnlistener *listener
      = evconnlistener_new_bind(base, listener_cb, base,
                    LEV_OPT_REUSEABLE|LEV_OPT_CLOSE_ON_FREE,
                    10, (struct sockaddr*)&sin,
                    sizeof(struct sockaddr_in));

  event_base_dispatch(base);

  evconnlistener_free(listener);
  event_base_free(base);

  return 0;
}


//             
void listener_cb(evconnlistener *listener, evutil_socket_t fd,
         struct sockaddr *sock, int socklen, void *arg)
{
  printf("accept a client %d
"
, fd); event_base *base = (event_base*)arg; // bufferevent bufferevent *bev = bufferevent_socket_new(base, fd, BEV_OPT_CLOSE_ON_FREE); bufferevent_setcb(bev, socket_read_cb, NULL, socket_event_cb, NULL); bufferevent_enable(bev, EV_READ | EV_PERSIST); } void socket_read_cb(bufferevent *bev, void *arg) { char msg[4096]; size_t len = bufferevent_read(bev, msg, sizeof(msg)-1 ); msg[len] = '\0'; printf("server read the data %s
"
, msg); char reply[] = "I has read your data"; bufferevent_write(bev, reply, strlen(reply) ); } void socket_event_cb(bufferevent *bev, short events, void *arg) { if (events & BEV_EVENT_EOF) printf("connection closed
"
); else if (events & BEV_EVENT_ERROR) printf("some other error
"
); // close free bufferevent_free(bev); }

좋은 웹페이지 즐겨찾기