summaryrefslogtreecommitdiff
path: root/src/lib/dlt_user.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/dlt_user.c')
-rw-r--r--src/lib/dlt_user.c162
1 files changed, 125 insertions, 37 deletions
diff --git a/src/lib/dlt_user.c b/src/lib/dlt_user.c
index ae076ca..ccebd4f 100644
--- a/src/lib/dlt_user.c
+++ b/src/lib/dlt_user.c
@@ -54,10 +54,21 @@
#include <unistd.h>
#include <stdbool.h>
-#ifdef DLT_USE_UNIX_SOCKET_IPC
-# include <sys/un.h>
+
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
# include <sys/socket.h>
#endif
+#ifdef DLT_LIB_USE_UNIX_SOCKET_IPC
+# include <sys/un.h>
+#endif
+#ifdef DLT_LIB_USE_VSOCK_IPC
+# ifdef linux
+# include <linux/vm_sockets.h>
+# endif
+# ifdef __QNX__
+# include <vm_sockets.h>
+# endif
+#endif
#include "dlt_user.h"
#include "dlt_common.h"
@@ -81,7 +92,7 @@ static DltUser dlt_user;
static bool dlt_user_initialised = false;
static int dlt_user_freeing = 0;
-#ifndef DLT_USE_UNIX_SOCKET_IPC
+#ifdef DLT_LIB_USE_FIFO_IPC
static char dlt_user_dir[DLT_PATH_MAX];
static char dlt_daemon_fifo[DLT_PATH_MAX];
#endif
@@ -209,13 +220,33 @@ DltReturnValue dlt_user_check_library_version(const char *user_major_version, co
return DLT_RETURN_OK;
}
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
+static DltReturnValue dlt_socket_set_nonblock_and_linger(int sockfd)
+{
+ int status;
+ struct linger l_opt;
+
+ status = fcntl(sockfd, F_SETFL, fcntl(sockfd, F_GETFL, 0) | O_NONBLOCK);
+ if (status == -1) {
+ dlt_log(LOG_INFO, "Socket cannot be changed to NON BLOCK\n");
+ return DLT_RETURN_ERROR;
+ }
+
+ l_opt.l_onoff = 1;
+ l_opt.l_linger = 10;
+
+ if (setsockopt(sockfd, SOL_SOCKET, SO_LINGER, &l_opt, sizeof l_opt) < 0)
+ dlt_log(LOG_WARNING, "Failed to set socket linger option\n");
+
+ return DLT_RETURN_OK;
+}
+#endif
+
+#ifdef DLT_LIB_USE_UNIX_SOCKET_IPC
static DltReturnValue dlt_initialize_socket_connection(void)
{
struct sockaddr_un remote;
- int status = 0;
char dltSockBaseDir[DLT_IPC_PATH_MAX];
- struct linger l_opt;
DLT_SEM_LOCK();
int sockfd = socket(AF_UNIX, SOCK_STREAM, 0);
@@ -226,22 +257,12 @@ static DltReturnValue dlt_initialize_socket_connection(void)
return DLT_RETURN_ERROR;
}
- status = fcntl(sockfd, F_SETFL, fcntl(sockfd, F_GETFL, 0) | O_NONBLOCK);
-
- if (status == -1) {
- dlt_vlog(LOG_INFO,
- "Socket %s/dlt cannot be changed to NON BLOCK\n",
- DLT_USER_IPC_PATH);
+ if (dlt_socket_set_nonblock_and_linger(sockfd) != DLT_RETURN_OK) {
+ close(sockfd);
+ DLT_SEM_FREE();
return DLT_RETURN_ERROR;
}
- /* Set SO_LINGER opt for the new client socket. */
- l_opt.l_onoff = 1;
- l_opt.l_linger = 10;
-
- if (setsockopt(sockfd, SOL_SOCKET, SO_LINGER, &l_opt, sizeof l_opt) < 0)
- dlt_log(LOG_WARNING, "Failed to set linger option\n");
-
remote.sun_family = AF_UNIX;
snprintf(dltSockBaseDir, DLT_IPC_PATH_MAX, "%s/dlt", DLT_USER_IPC_PATH);
strncpy(remote.sun_path, dltSockBaseDir, sizeof(remote.sun_path));
@@ -268,8 +289,10 @@ static DltReturnValue dlt_initialize_socket_connection(void)
if (dlt_receiver_init(&(dlt_user.receiver),
sockfd,
+ DLT_RECEIVE_SOCKET,
DLT_USER_RCVBUF_MAX_SIZE) == DLT_RETURN_ERROR) {
dlt_user_initialised = false;
+ close(sockfd);
DLT_SEM_FREE();
return DLT_RETURN_ERROR;
}
@@ -279,7 +302,62 @@ static DltReturnValue dlt_initialize_socket_connection(void)
return DLT_RETURN_OK;
}
-#else /* setup fifo*/
+#elif defined DLT_LIB_USE_VSOCK_IPC
+static DltReturnValue dlt_initialize_vsock_connection()
+{
+ struct sockaddr_vm remote;
+
+ DLT_SEM_LOCK();
+ int sockfd = socket(AF_VSOCK, SOCK_STREAM, 0);
+
+ if (sockfd == DLT_FD_INIT) {
+ dlt_log(LOG_CRIT, "Failed to create VSOCK socket\n");
+ DLT_SEM_FREE();
+ return DLT_RETURN_ERROR;
+ }
+
+ memset(&remote, 0, sizeof(remote));
+ remote.svm_family = AF_VSOCK;
+ remote.svm_port = DLT_VSOCK_PORT;
+ remote.svm_cid = VMADDR_CID_HOST;
+
+ if (connect(sockfd, (struct sockaddr *)&remote, sizeof(remote)) == -1) {
+ if (dlt_user.connection_state != DLT_USER_RETRY_CONNECT) {
+ dlt_vlog(LOG_INFO, "VSOCK socket cannot be opened. Retrying later...\n");
+ dlt_user.connection_state = DLT_USER_RETRY_CONNECT;
+ }
+
+ close(sockfd);
+ dlt_user.dlt_log_handle = -1;
+ }
+ else {
+ /* Set to non-blocking after connect() to avoid EINPROGRESS. DltUserConntextionState
+ needs "connecting" state if connect() should be non-blocking. */
+ if (dlt_socket_set_nonblock_and_linger(sockfd) != DLT_RETURN_OK) {
+ close(sockfd);
+ DLT_SEM_FREE();
+ return DLT_RETURN_ERROR;
+ }
+
+ dlt_user.dlt_log_handle = sockfd;
+ dlt_user.connection_state = DLT_USER_CONNECTED;
+
+ if (dlt_receiver_init(&(dlt_user.receiver),
+ sockfd,
+ DLT_RECEIVE_SOCKET,
+ DLT_USER_RCVBUF_MAX_SIZE) == DLT_RETURN_ERROR) {
+ dlt_user_initialised = false;
+ close(sockfd);
+ DLT_SEM_FREE();
+ return DLT_RETURN_ERROR;
+ }
+ }
+
+ DLT_SEM_FREE();
+
+ return DLT_RETURN_OK;
+}
+#else /* DLT_LIB_USE_FIFO_IPC */
static DltReturnValue dlt_initialize_fifo_connection(void)
{
char filename[DLT_PATH_MAX];
@@ -383,7 +461,7 @@ DltReturnValue dlt_init(void)
#endif
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#ifdef DLT_LIB_USE_UNIX_SOCKET_IPC
if (dlt_initialize_socket_connection() != DLT_RETURN_OK)
/* We could connect to the pipe, but not to the socket, which is normally */
@@ -391,12 +469,19 @@ DltReturnValue dlt_init(void)
/* in case application is started before daemon, it is expected behaviour */
return DLT_RETURN_ERROR;
-#else /* FIFO connection */
+#elif defined DLT_LIB_USE_VSOCK_IPC
+
+ if (dlt_initialize_vsock_connection() != DLT_RETURN_OK)
+ return DLT_RETURN_ERROR;
+
+#else /* DLT_LIB_USE_FIFO_IPC */
if (dlt_initialize_fifo_connection() != DLT_RETURN_OK)
return DLT_RETURN_ERROR;
- if (dlt_receiver_init(&(dlt_user.receiver), dlt_user.dlt_user_handle,
+ if (dlt_receiver_init(&(dlt_user.receiver),
+ dlt_user.dlt_user_handle,
+ DLT_RECEIVE_FD,
DLT_USER_RCVBUF_MAX_SIZE) == DLT_RETURN_ERROR) {
dlt_user_initialised = false;
return DLT_RETURN_ERROR;
@@ -821,7 +906,7 @@ DltReturnValue dlt_free(void)
{
uint32_t i;
int ret = 0;
-#ifndef DLT_USE_UNIX_SOCKET_IPC
+#ifdef DLT_LIB_USE_FIFO_IPC
char filename[DLT_PATH_MAX];
#endif
@@ -841,7 +926,7 @@ DltReturnValue dlt_free(void)
dlt_stop_threads();
-#ifndef DLT_USE_UNIX_SOCKET_IPC
+#ifdef DLT_LIB_USE_FIFO_IPC
if (dlt_user.dlt_user_handle != DLT_FD_INIT) {
close(dlt_user.dlt_user_handle);
@@ -859,7 +944,7 @@ DltReturnValue dlt_free(void)
if (dlt_user.dlt_log_handle != -1) {
/* close log file/output fifo to daemon */
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
ret = shutdown(dlt_user.dlt_log_handle, SHUT_WR);
if (ret < 0) {
@@ -3752,7 +3837,7 @@ DltReturnValue dlt_user_log_send_log(DltContextData *log, int mtype)
/* handle not open or pipe error */
close(dlt_user.dlt_log_handle);
dlt_user.dlt_log_handle = -1;
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
dlt_user.connection_state = DLT_USER_RETRY_CONNECT;
#endif
@@ -4126,7 +4211,6 @@ DltReturnValue dlt_user_log_check_user_message(void)
uint32_t i;
int fd;
- DltReceiverType from_src_type = DLT_RECEIVE_FD;
struct pollfd nfd[1];
DltUserHeader *userheader;
@@ -4150,20 +4234,18 @@ DltReturnValue dlt_user_log_check_user_message(void)
delayed_log_level_changed_callback.log_level_changed_callback = 0;
delayed_injection_callback.data = 0;
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
fd = dlt_user.dlt_log_handle;
- from_src_type = DLT_RECEIVE_SOCKET;
-#else
+#else /* DLT_LIB_USE_FIFO_IPC */
fd = dlt_user.dlt_user_handle;
- from_src_type = DLT_RECEIVE_FD;
#endif
nfd[0].events = POLLIN;
nfd[0].fd = fd;
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#if defined DLT_LIB_USE_UNIX_SOCKET_IPC || defined DLT_LIB_USE_VSOCK_IPC
if (fd != DLT_FD_INIT) {
ret = poll(nfd, 1, -1);
-#else
+#else /* DLT_LIB_USE_FIFO_IPC */
if (fd != DLT_FD_INIT && dlt_user.dlt_log_handle > 0) {
ret = poll(nfd, 1, DLT_USER_RECEIVE_NDELAY);
#endif
@@ -4173,7 +4255,7 @@ DltReturnValue dlt_user_log_check_user_message(void)
return DLT_RETURN_ERROR;
}
- if (dlt_receiver_receive(receiver, from_src_type) <= 0)
+ if (dlt_receiver_receive(receiver) <= 0)
/* No new message available */
return DLT_RETURN_OK;
@@ -4502,7 +4584,7 @@ void dlt_user_log_reattach_to_daemon(void)
if (dlt_user.dlt_log_handle < 0) {
dlt_user.dlt_log_handle = DLT_FD_INIT;
-#ifdef DLT_USE_UNIX_SOCKET_IPC
+#ifdef DLT_LIB_USE_UNIX_SOCKET_IPC
/* try to open connection to dlt daemon */
dlt_initialize_socket_connection();
@@ -4510,7 +4592,13 @@ void dlt_user_log_reattach_to_daemon(void)
/* return if not connected */
return;
-#else
+#elif defined DLT_LIB_USE_VSOCK_IPC
+ dlt_initialize_vsock_connection();
+
+ if (dlt_user.connection_state != DLT_USER_CONNECTED)
+ return;
+
+#else /* DLT_LIB_USE_FIFO_IPC */
/* try to open pipe to dlt daemon */
int fd = open(dlt_daemon_fifo, O_WRONLY | O_NONBLOCK);