summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBui Nguyen Quoc Thanh <49302843+thanhbnq@users.noreply.github.com>2022-09-28 15:22:59 +0700
committerGitHub <noreply@github.com>2022-09-28 10:22:59 +0200
commit5bce13c1fd5dafafb383883f016cfa3762b730f5 (patch)
treee541ec78fba5182b44a6488d5dd68d34a4979ad4
parenta6c42a0c5c67e764d964f91234b9c8c0f9d09b54 (diff)
downloadDLT-daemon-5bce13c1fd5dafafb383883f016cfa3762b730f5.tar.gz
dlt_client:Block in connect() (#409)
Connect TCP socket with non-blocking socket Check errno and getsockopt to guarantee that the socket connection is established successfully Signed-off-by: Le Tin <tin.le@vn.bosch.com> Signed-off-by: Le Tin <tin.le@vn.bosch.com>
-rw-r--r--src/lib/dlt_client.c72
1 files changed, 66 insertions, 6 deletions
diff --git a/src/lib/dlt_client.c b/src/lib/dlt_client.c
index 174cfa0..245ebef 100644
--- a/src/lib/dlt_client.c
+++ b/src/lib/dlt_client.c
@@ -91,6 +91,7 @@
#include <string.h> /* for strlen(), memcmp(), memmove() */
#include <errno.h>
#include <limits.h>
+#include <poll.h>
#include "dlt_types.h"
#include "dlt_client.h"
@@ -171,13 +172,19 @@ DltReturnValue dlt_client_init(DltClient *client, int verbose)
DltReturnValue dlt_client_connect(DltClient *client, int verbose)
{
const int yes = 1;
- char portnumbuffer[33];
+ char portnumbuffer[33] = {0};
struct addrinfo hints, *servinfo, *p;
struct sockaddr_un addr;
int rv;
struct ip_mreq mreq;
DltReceiverType receiver_type = DLT_RECEIVE_FD;
+ struct pollfd pfds[1];
+ int ret;
+ int n;
+ socklen_t m = sizeof(n);
+ int connect_errno = 0;
+
memset(&hints, 0, sizeof(hints));
hints.ai_socktype = SOCK_STREAM;
@@ -205,27 +212,80 @@ DltReturnValue dlt_client_connect(DltClient *client, int verbose)
continue;
}
- if (connect(client->sock, p->ai_addr, p->ai_addrlen) < 0) {
+ /* Set socket to Non-blocking mode */
+ if(fcntl(client->sock, F_SETFL, fcntl(client->sock,F_GETFL,0) | O_NONBLOCK) < 0)
+ {
+ dlt_vlog(LOG_WARNING,
+ "%s: Socket cannot be changed to NON BLOCK: %s\n",
+ __func__, strerror(errno));
close(client->sock);
continue;
}
+ if (connect(client->sock, p->ai_addr, p->ai_addrlen) < 0) {
+ if (errno == EINPROGRESS) {
+ pfds[0].fd = client->sock;
+ pfds[0].events = POLLOUT;
+ ret = poll(pfds, 1, 500);
+ if (ret < 0) {
+ dlt_vlog(LOG_ERR, "%s: Failed to poll with err [%s]\n",
+ __func__, strerror(errno));
+ close(client->sock);
+ continue;
+ }
+ else if ((pfds[0].revents & POLLOUT) &&
+ getsockopt(client->sock, SOL_SOCKET,
+ SO_ERROR, (void*)&n, &m) == 0) {
+ if (n == 0) {
+ dlt_vlog(LOG_DEBUG, "%s: Already connect\n", __func__);
+ if(fcntl(client->sock, F_SETFL,
+ fcntl(client->sock,F_GETFL,0) & ~O_NONBLOCK) < 0) {
+ dlt_vlog(LOG_WARNING,
+ "%s: Socket cannot be changed to BLOCK with err [%s]\n",
+ __func__, strerror(errno));
+ close(client->sock);
+ continue;
+ }
+ }
+ else {
+ connect_errno = n;
+ close(client->sock);
+ continue;
+ }
+ }
+ else {
+ connect_errno = errno;
+ close(client->sock);
+ continue;
+ }
+ }
+ else {
+ connect_errno = errno;
+ close(client->sock);
+ continue;
+ }
+ }
+
break;
}
freeaddrinfo(servinfo);
if (p == NULL) {
+ dlt_vlog(LOG_ERR,
+ "%s: ERROR: failed to connect! %s\n",
+ __func__,
+ strerror(connect_errno));
+ return DLT_RETURN_ERROR;
+ }
+
+ if (verbose) {
dlt_vlog(LOG_INFO,
"%s: Connected to DLT daemon (%s)\n",
__func__,
client->servIP);
- return DLT_RETURN_ERROR;
}
- if (verbose)
- printf("Connected to DLT daemon (%s)\n", client->servIP);
-
receiver_type = DLT_RECEIVE_SOCKET;
break;