Optimize the perf / validate FD.
authorSung-jae Park <nicesj.park@samsung.com>
Thu, 20 Mar 2014 13:00:32 +0000 (22:00 +0900)
committerSung-jae Park <nicesj.park@samsung.com>
Fri, 21 Mar 2014 00:08:42 +0000 (09:08 +0900)
Reduce the malloc for handling the receive context.
Validate socket FD.

Change-Id: Ia492e7d0a23dd233f6227676aa2beee94d106a6c

src/com-core.c
src/com-core_packet.c

index dfbb309..d254014 100644 (file)
@@ -23,6 +23,7 @@
 #include <stdlib.h>
 #include <sys/time.h>
 #include <sys/types.h>
+#include <sys/socket.h>
 
 #include <glib.h>
 
@@ -102,6 +103,20 @@ HAPI void invoke_disconn_cb_list(int handle)
        s_info.processing_event_callback &= ~PROCESSING_DISCONNECTION;
 }
 
+static int validate_handle(int fd)
+{
+       int error;
+       socklen_t len;
+
+       len = sizeof(error);
+       if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &error, &len) < 0) {
+               ErrPrint("getsockopt: %s\n", strerror(errno));
+               return 0;
+       }
+
+       return !(error == EBADF);
+}
+
 static gboolean client_cb(GIOChannel *src, GIOCondition cond, gpointer data)
 {
        int client_fd;
@@ -132,7 +147,8 @@ static gboolean client_cb(GIOChannel *src, GIOCondition cond, gpointer data)
                return FALSE;
        }
 
-       return TRUE;
+       /* Check whether the socket FD is closed or not */
+       return validate_handle(client_fd) ? TRUE : FALSE;
 }
 
 static gboolean accept_cb(GIOChannel *src, GIOCondition cond, gpointer cbdata)
@@ -200,7 +216,7 @@ static gboolean accept_cb(GIOChannel *src, GIOCondition cond, gpointer cbdata)
        g_io_channel_unref(gio);
 
        invoke_con_cb_list(client_fd);
-       return TRUE;
+       return validate_handle(socket_fd) ? TRUE : FALSE;
 }
 
 EAPI int com_core_server_create(const char *addr, int is_sync, int (*service_cb)(int fd, void *data), void *data)
index 75744fc..6c0146d 100644 (file)
@@ -164,6 +164,20 @@ static inline struct recv_ctx *find_recv_ctx(int handle)
        return NULL;
 }
 
+static inline void recreate_recv_ctx(struct recv_ctx *ctx)
+{
+       if (ctx->packet) {
+               packet_destroy(ctx->packet);
+               ctx->packet = NULL;
+       }
+       ctx->state = RECV_STATE_INIT;
+       ctx->offset = 0;
+       ctx->pid = (pid_t)-1;
+       // ctx->inuse
+       // ctx->handle
+       // ctx->timeout
+}
+
 static inline void destroy_recv_ctx(struct recv_ctx *ctx)
 {
        struct dlist *l;
@@ -448,7 +462,10 @@ static int service_cb(int handle, void *data)
        if (receive->state == RECV_STATE_READY) {
                ret = packet_ready(handle, receive, data);
                if (ret == 0) {
-                       destroy_recv_ctx(receive);
+                       /*!
+                        * If ret is negative value, the receive context will be destroyed from disconnected callback
+                        */
+                       recreate_recv_ctx(receive);
                }
                /*!
                 * if ret is negative value, disconnected_cb will be called after this function