Handling G_IO_STATUS_AGAIN for rfcomm client 75/234275/2 accepted/tizen/unified/20200529.124350 submit/tizen/20200527.022320
authorinjun.yang <injun.yang@samsung.com>
Wed, 20 May 2020 09:28:32 +0000 (18:28 +0900)
committerPyun DoHyun <dh79.pyun@samsung.com>
Mon, 25 May 2020 23:12:20 +0000 (23:12 +0000)
[Model] All
[BinType] AP
[Customer] OPEN

[Issue#] P200520-00225
[Request] Internal
[Occurrence Version] N/A

[Problem] G_IO_STATUS_AGAIN repeated
[Cause & Measure] if G_IO_STATUS_AGAIN repeated then close socket
[Checking Method] n/a

[Team] Convergence BT
[Developer] Injun Yang
[Solution company] Samsung
[Change Type] Specification change

Change-Id: I11d4218e6a3c75136bd792dae8edd05e5dd00841
Signed-off-by: injun.yang <injun.yang@samsung.com>
Signed-off-by: Wootak Jung <wootak.jung@samsung.com>
bt-api/bt-rfcomm-client.c

index 0e4b1e7..eb95987 100644 (file)
@@ -368,6 +368,7 @@ static gboolean __client_data_received_cb(GIOChannel *chan, GIOCondition cond,
        GIOStatus status = G_IO_STATUS_NORMAL;
        GError *err = NULL;
        int fd;
+       static int resource_unavailable_cnt = 0;
 
        retv_if(info == NULL, FALSE);
        fd = g_io_channel_unix_get_fd(chan);
@@ -396,35 +397,31 @@ static gboolean __client_data_received_cb(GIOChannel *chan, GIOCondition cond,
                BT_ERR("IO Channel read is failed with %d", status);
 
                g_free(buffer);
-               if (err || status == G_IO_STATUS_EOF) {
-                       if (err)
-                               BT_ERR("IO Channel read error [%s]", err->message);
-                       if ((status == G_IO_STATUS_EOF) ||
-                                       (status == G_IO_STATUS_ERROR &&
-                                       __is_error_by_disconnect(err))) {
+
+               if (err) {
+                       BT_ERR("IO Channel read error [%s]", err->message);
+                       if (status == G_IO_STATUS_ERROR &&
+                                       __is_error_by_disconnect(err)) {
 
                                BT_ERR("cond : %d", cond);
-                               if (err)
-                                       g_error_free(err);
-
-                               conn_info = __get_conn_info_from_fd(info, fd);
-                               if (conn_info == NULL) {
-                                       BT_ERR("No Connection info found with FD [%d]", fd);
-                                       return FALSE;
-                               }
-
-                               if (conn_info->disconnected == FALSE) {
-                                       close(conn_info->fd);
-                                       conn_info->disconnected = TRUE;
-                               }
-                               __rfcomm_client_disconnect(info);
-                               return FALSE;
-                       }
-                       if (err)
                                g_error_free(err);
+                               goto fail;
+                       }
+                       g_error_free(err);
+               }
+
+               if (status == G_IO_STATUS_ERROR ||
+                       status == G_IO_STATUS_EOF) {
+                       goto fail;
+               } else if (status == G_IO_STATUS_AGAIN) {
+                       resource_unavailable_cnt++;
+                       if (resource_unavailable_cnt > 10)
+                               goto fail;
                }
+
                return TRUE;
        }
+       resource_unavailable_cnt = 0;
 
        event_info = _bt_event_get_cb_data(BT_RFCOMM_CLIENT_EVENT);
        if (event_info == NULL) {
@@ -450,6 +447,21 @@ static gboolean __client_data_received_cb(GIOChannel *chan, GIOCondition cond,
 
        g_free(buffer);
        return TRUE;
+
+fail:
+       conn_info = __get_conn_info_from_fd(info, fd);
+       if (conn_info == NULL) {
+               BT_ERR("No Connection info found with FD [%d]", fd);
+               return FALSE;
+       }
+
+       if (conn_info->disconnected == FALSE) {
+               close(conn_info->fd);
+               conn_info->disconnected = TRUE;
+       }
+       __rfcomm_client_disconnect(info);
+
+       return FALSE;
 }
 
 static void __client_connected_cb(rfcomm_cb_data_t *cb_data, char *dev_address,