libevent - does this c++ code have memory leaks? -


i'm trying understand libevent c++ code got this page.
i'm bit confused - correct think code might have memory leaks?

it seems connectiondata pointer created in on_connect() callback, delete() called on bad read or after write complete.
if connection accept()ed - there no reads or writes? pointer stays in daemon memory?

#include <event.h> #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <arpa/inet.h>  #include <iostream>  // read/write buffer max length static const size_t max_buf = 512;  typedef struct {     struct event ev;     char         buf[max_buf];     size_t       offset;     size_t       size; } connectiondata;  void on_connect(int fd, short event, void *arg); void client_read(int fd, short event, void *arg); void client_write(int fd, short event, void *arg);  int main(int argc, char **argv) {     // check arguments     if (argc < 3) {         std::cout << "run options: <ip address> <port>" << std::endl;         return 1;     }     // create server socket     int server_sock = socket(af_inet, sock_stream, 0);     if (server_sock == -1) {         std::cerr << "failed create socket" << std::endl;         return 1;     }      sockaddr_in sa;     int         on      = 1;     char      * ip_addr = argv[1];     short       port    = atoi(argv[2]);      sa.sin_family       = af_inet;     sa.sin_port         = htons(port);     sa.sin_addr.s_addr  = inet_addr(ip_addr);      // set option so_reuseaddr reuse same host:port in short time     if (setsockopt(server_sock, sol_socket, so_reuseaddr, &on, sizeof(on)) == -1) {         std::cerr << "failed set option so_reuseaddr" << std::endl;         return 1;     }      // bind server socket ip:port     if (bind(server_sock, reinterpret_cast<const sockaddr*>(&sa), sizeof(sa)) == -1) {         std::cerr << "failed bind server socket" << std::endl;         return 1;     }      // make server listen     if (listen(server_sock, 10) == -1) {         std::cerr << "failed make server listen" << std::endl;         return 1;     }      // init events     struct event evserver_sock;     // initialize     event_init();     // set connection callback (on_connect()) read event on server socket     event_set(&evserver_sock, server_sock, ev_read, on_connect, &evserver_sock);     // add server event without timeout     event_add(&evserver_sock, null);      // dispatch events     event_dispatch();      return 0; }  // handle new connection {{{ void on_connect(int fd, short event, void *arg)  {     sockaddr_in client_addr;     socklen_t   len = 0;      // accept incoming connection     int sock = accept(fd, reinterpret_cast<sockaddr*>(&client_addr), &len);     if (sock < 1) {          return;      }      // set read callback client socket     connectiondata * data = new connectiondata;     event_set(&data->ev, sock, ev_read, client_read, data);     // reschedule server event     event_add(reinterpret_cast<struct event*>(arg), null);     // schedule client event     event_add(&data->ev, null); } //}}}  // handle client request {{{ void client_read(int fd, short event, void *arg) {     connectiondata * data = reinterpret_cast<connectiondata*>(arg);     if (!data) {         close(fd);         return;     }     int len = read(fd, data->buf, max_buf - 1);     if (len < 1) {         close(fd);         delete data;         return;     }     data->buf[len] = 0;     data->size     = len;     data->offset   = 0;     // set write callback client socket     event_set(&data->ev, fd, ev_write, client_write, data);     // schedule client event     event_add(&data->ev, null); } //}}}  // handle client responce {{{ void client_write(int fd, short event, void *arg) {     connectiondata * data = reinterpret_cast<connectiondata*>(arg);     if (!data) {         close(fd);         return;     }     // send data client     int len = write(fd, data->buf + data->offset, data->size - data->offset);     if (len < data->size - data->offset) {         // failed send rest data, need reschedule         data->offset += len;         event_set(&data->ev, fd, ev_write, client_write, data);         // schedule client event         event_add(&data->ev, null);     }     close(fd);     delete data; } //}}} 

the documentation event_set says valid event types ev_read or ev_write, callback invoked ev_timeout, ev_signal, ev_read, or ev_write. documentation not clear, expect read callback invoked when socket closed client. expect delete in failure branch in client_read handle situation.

note that case if client sends fin or rst packet. client establish connection , leave open forever. reason, code should modified have timeout (perhaps via event_once) , require client send message within timeout.


Comments

Popular posts from this blog

google api - Incomplete response from Gmail API threads.list -

Installing Android SQLite Asset Helper -

Qt Creator - Searching files with Locator including folder -