#include "dlt_user_shared.h"
#include "dlt_user_shared_cfg.h"
#include "dlt_user_cfg.h"
-#include "dlt_queue.h"
static DltUser dlt_user;
static int dlt_user_initialised = 0;
/* Segmented Network Trace */
#define DLT_MAX_TRACE_SEGMENT_SIZE 1024
#define DLT_MESSAGE_QUEUE_NAME "/dlt_message_queue"
-#define DLT_DELAYED_RESEND_INDICATOR_PATTERN 0xFFFFFFFF
+#define DLT_DELAYED_RESEND_INDICATOR_PATTERN 0xFFFF
+/* Mutex to wait on while message queue is not initialized */
+pthread_mutex_t mq_mutex;
+pthread_cond_t mq_init_condition;
+
+/* Structure to pass data to segmented thread */
typedef struct {
DltContext *handle;
uint16_t id;
void *payload;
} s_segmented_data;
-dlt_queue *dlt_segmented_nwt_queue;
-
/* Function prototypes for internally used functions */
static void dlt_user_receiverthread_function(void *ptr);
static void dlt_user_atexit_handler(void);
static void dlt_user_log_reattach_to_daemon(void);
static int dlt_user_log_send_overflow(void);
static void dlt_user_trace_network_segmented_thread(void *unused);
+static void dlt_user_trace_network_segmented_thread_segmenter(s_segmented_data *data);
+static int dlt_user_queue_resend(void);
int dlt_user_check_library_version(const char *user_major_version,const char *user_minor_version){
dlt_log(LOG_WARNING, "Can't destroy thread attributes!\n");
}
- /* Generate per process name for queue */
- char queue_name[NAME_MAX];
- sprintf(queue_name, "%s.%d", DLT_MESSAGE_QUEUE_NAME, getpid());
+ /* These will be lazy initialized only when needed */
+ dlt_user.dlt_segmented_queue_read_handle = -1;
+ dlt_user.dlt_segmented_queue_write_handle = -1;
- /* Maximum queue size is 10, limit to size of pointers */
- struct mq_attr mqatr;
- mqatr.mq_flags = 0;
- mqatr.mq_maxmsg = 10;
- mqatr.mq_msgsize = sizeof(s_segmented_data *);
- mqatr.mq_curmsgs = 0;
-
- /* Separate handles for reading and writing */
- dlt_user.dlt_segmented_queue_read_handle = mq_open(queue_name, O_CREAT| O_RDONLY,
- S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH, &mqatr);
- if(dlt_user.dlt_segmented_queue_read_handle < 0)
- {
- dlt_log(LOG_CRIT, "Can't create message queue read handle!\n");
- dlt_log(LOG_CRIT, strerror(errno));
- return -1;
- }
-
- dlt_user.dlt_segmented_queue_write_handle = mq_open(queue_name, O_WRONLY);
- if(dlt_user.dlt_segmented_queue_write_handle < 0)
- {
- dlt_log(LOG_CRIT, "Can't open message queue write handle!\n");
- dlt_log(LOG_CRIT, strerror(errno));
- return -1;
- }
+ /* Wait mutext for segmented thread */
+ pthread_mutex_init(&mq_mutex, NULL);
+ pthread_cond_init(&mq_init_condition, NULL);
+ /* Start the segmented thread */
if(pthread_create(&(dlt_user.dlt_segmented_nwt_handle), NULL,
(void *)dlt_user_trace_network_segmented_thread, NULL))
{
return 0;
}
+int dlt_init_message_queue(void)
+{
+ pthread_mutex_lock(&mq_mutex);
+ if(dlt_user.dlt_segmented_queue_read_handle >= 0 &&
+ dlt_user.dlt_segmented_queue_write_handle >= 0)
+ {
+ // Already intialized
+ pthread_mutex_unlock(&mq_mutex);
+ return 0;
+ }
+
+ /* Generate per process name for queue */
+ char queue_name[NAME_MAX];
+ sprintf(queue_name, "%s.%d", DLT_MESSAGE_QUEUE_NAME, getpid());
+
+ /* Maximum queue size is 10, limit to size of pointers */
+ struct mq_attr mqatr;
+ mqatr.mq_flags = 0;
+ mqatr.mq_maxmsg = 10;
+ mqatr.mq_msgsize = sizeof(s_segmented_data *);
+ mqatr.mq_curmsgs = 0;
+
+ /**
+ * Create the message queue. It must be newly created
+ * if old one was left by a crashing process.
+ * */
+ dlt_user.dlt_segmented_queue_read_handle = mq_open(queue_name, O_CREAT| O_RDONLY | O_EXCL,
+ S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH, &mqatr);
+ if(dlt_user.dlt_segmented_queue_read_handle < 0)
+ {
+ if(errno == EEXIST)
+ {
+ dlt_log(LOG_WARNING, "Old message queue exists, trying to delete.\n");
+ if(mq_unlink(queue_name) < 0)
+ {
+ char str[256];
+ snprintf(str,255,"Could not delete existing message queue!: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
+ }
+ else // Retry
+ {
+ dlt_user.dlt_segmented_queue_read_handle = mq_open(queue_name, O_CREAT| O_RDONLY | O_EXCL,
+ S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH, &mqatr);
+ }
+ }
+ if(dlt_user.dlt_segmented_queue_read_handle < 0)
+ {
+ char str[256];
+ snprintf(str,255,"Can't create message queue read handle!: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
+ pthread_mutex_unlock(&mq_mutex);
+ return -1;
+ }
+ }
+
+ dlt_user.dlt_segmented_queue_write_handle = mq_open(queue_name, O_WRONLY|O_NONBLOCK);
+ if(dlt_user.dlt_segmented_queue_write_handle < 0)
+ {
+
+ char str[256];
+ snprintf(str,255,"Can't open message queue write handle!: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
+ pthread_mutex_unlock(&mq_mutex);
+ return -1;
+ }
+
+ pthread_cond_signal(&mq_init_condition);
+ pthread_mutex_unlock(&mq_mutex);
+ return 0;
+}
+
int dlt_init_common(void)
{
char *env_local_print;
}
/* Initialize LogLevel/TraceStatus field */
+ DLT_SEM_LOCK();
dlt_user.dlt_ll_ts = 0;
dlt_user.dlt_ll_ts_max_num_entries = 0;
dlt_user.dlt_ll_ts_num_entries = 0;
if (dlt_buffer_init_dynamic(&(dlt_user.startup_buffer), DLT_USER_RINGBUFFER_MIN_SIZE, DLT_USER_RINGBUFFER_MAX_SIZE, DLT_USER_RINGBUFFER_STEP_SIZE)==-1)
{
dlt_user_initialised = 0;
+ DLT_SEM_FREE();
return -1;
}
+ DLT_SEM_FREE();
signal(SIGPIPE,SIG_IGN); /* ignore pipe signals */
void dlt_user_atexit_handler(void)
{
+ if (dlt_user_initialised==0)
+ {
+ return;
+ }
/* Try to resend potential log messages in the user buffer */
int count = dlt_user_atexit_blow_out_user_buffer();
/* Ignore return value */
dlt_buffer_free_dynamic(&(dlt_user.startup_buffer));
+ DLT_SEM_LOCK();
if (dlt_user.dlt_ll_ts)
{
for (i=0;i<dlt_user.dlt_ll_ts_max_num_entries;i++)
dlt_user.dlt_ll_ts_max_num_entries = 0;
dlt_user.dlt_ll_ts_num_entries = 0;
}
+ DLT_SEM_FREE();
if (dlt_user.dlt_segmented_nwt_handle)
{
char queue_name[NAME_MAX];
sprintf(queue_name, "%s.%d", DLT_MESSAGE_QUEUE_NAME, getpid());
- if(mq_close(dlt_user.dlt_segmented_queue_write_handle) < 0)
- {
- dlt_log(LOG_ERR, "Failed to unlink message queue write handle!\n");
- dlt_log(LOG_ERR, strerror(errno));
- }
-
- if(mq_close(dlt_user.dlt_segmented_queue_read_handle) < 0 ||
- mq_unlink(queue_name))
- {
- dlt_log(LOG_ERR, "Failed to unlink message queue read handle!\n");
- dlt_log(LOG_ERR, strerror(errno));
- }
+ /**
+ * Ignore errors from these, to not to spam user if dlt_free
+ * is accidentally called multiple times.
+ */
+ mq_close(dlt_user.dlt_segmented_queue_write_handle);
+ mq_close(dlt_user.dlt_segmented_queue_read_handle);
+ mq_unlink(queue_name);
dlt_user_initialised = 0;
}
DLT_SEM_FREE();
+
+ if(dlt_user_queue_resend() < 0 && dlt_user.dlt_log_handle >= 0)
+ {
+ dlt_log(LOG_WARNING, "dlt_forward_msg: Failed to queue resending.\n");
+ }
}
switch (ret)
return -1;
}
- type_info = DLT_TYPE_INFO_STRG;
+ type_info = DLT_TYPE_INFO_STRG | DLT_SCOD_ASCII;
+
+ memcpy((log->buffer)+log->size,&(type_info),sizeof(uint32_t));
+ log->size += sizeof(uint32_t);
+ }
+
+ arg_size = strlen(text) + 1;
+
+ memcpy((log->buffer)+log->size,&(arg_size),sizeof(uint16_t));
+ log->size += sizeof(uint16_t);
+
+ memcpy((log->buffer)+log->size,text,arg_size);
+ log->size += arg_size;
+
+ log->args_num ++;
+
+ return 0;
+}
+
+int dlt_user_log_write_utf8_string(DltContextData *log, const char *text)
+{
+ uint16_t arg_size;
+ uint32_t type_info;
+
+ if ((log==0) || (text==0))
+ {
+ return -1;
+ }
+
+ arg_size = strlen(text)+1;
+
+ if ((log->size+arg_size+sizeof(uint16_t))>DLT_USER_BUF_MAX_SIZE)
+ {
+ return -1;
+ }
+
+ if (dlt_user.verbose_mode)
+ {
+ if ((log->size+arg_size+sizeof(uint32_t)+sizeof(uint16_t))>DLT_USER_BUF_MAX_SIZE)
+ {
+ return -1;
+ }
+
+ type_info = DLT_TYPE_INFO_STRG | DLT_SCOD_UTF8;
memcpy((log->buffer)+log->size,&(type_info),sizeof(uint32_t));
log->size += sizeof(uint32_t);
}
/* Write stream handle */
- if(dlt_user_log_write_uint(&log, *id) < 0)
+ if(dlt_user_log_write_uint16(&log, *id) < 0)
{
return -1;
}
}
/* Write size of payload */
- if(dlt_user_log_write_uint(&log, payload_len) < 0)
+ if(dlt_user_log_write_uint16(&log, payload_len) < 0)
{
return -1;
}
segment_count--;
}
- if(dlt_user_log_write_uint(&log, segment_count) < 0)
+ if(dlt_user_log_write_uint16(&log, segment_count) < 0)
{
return -1;
}
/* Write length of one segment */
- if(dlt_user_log_write_uint(&log, DLT_MAX_TRACE_SEGMENT_SIZE) < 0)
+ if(dlt_user_log_write_uint16(&log, DLT_MAX_TRACE_SEGMENT_SIZE) < 0)
{
return -1;
}
}
/* Write stream handle */
- if(dlt_user_log_write_uint(&log, id) < 0)
+ if(dlt_user_log_write_uint16(&log, id) < 0)
{
return -1;
}
/* Write segment sequence number */
- if(dlt_user_log_write_uint(&log, sequence) < 0)
+ if(dlt_user_log_write_uint16(&log, sequence) < 0)
{
return -1;
}
return 0;
}
+
void dlt_user_trace_network_segmented_thread(void *unused)
{
/* Unused on purpose. */
s_segmented_data *data;
- while(1)
- {
- ssize_t read = mq_receive(dlt_user.dlt_segmented_queue_read_handle, (char *)&data,
- sizeof(s_segmented_data * ), NULL);
- if(read != sizeof(s_segmented_data *))
- {
- dlt_log(LOG_ERR, "NWTSegmented: Error while reading queue.\n");
- dlt_log(LOG_ERR, strerror(errno));
- continue;
- }
+ while(1)
+ {
+ // Wait until message queue is initialized
+ pthread_mutex_lock(&mq_mutex);
+ if(dlt_user.dlt_segmented_queue_read_handle < 0)
+ {
+ pthread_cond_wait(&mq_init_condition, &mq_mutex);
+ }
+ pthread_mutex_unlock(&mq_mutex);
- /* Indicator just to try to flush the buffer */
- if(data == (s_segmented_data *)DLT_DELAYED_RESEND_INDICATOR_PATTERN)
- {
- dlt_user_log_resend_buffer();
- continue;
- }
+ ssize_t read = mq_receive(dlt_user.dlt_segmented_queue_read_handle, (char *)&data,
+ sizeof(s_segmented_data * ), NULL);
- /* Segment the data and send the chunks */
- void *ptr = NULL;
- uint16_t offset = 0;
- uint16_t sequence = 0;
- do
- {
- uint16_t len = 0;
- if(offset + DLT_MAX_TRACE_SEGMENT_SIZE > data->payload_len)
- {
- len = data->payload_len - offset;
- }
- else
- {
- len = DLT_MAX_TRACE_SEGMENT_SIZE;
- }
- /* If payload size aligns perfectly with segment size, avoid sendind empty segment */
- if(len == 0)
- {
- break;
- }
+ if(read != sizeof(s_segmented_data *))
+ {
- ptr = data->payload + offset;
- DltReturnValue err = dlt_user_trace_network_segmented_segment(data->id, data->handle, data->nw_trace_type, sequence++, len, ptr);
- if(err == DLT_RETURN_BUFFER_FULL || err == DLT_RETURN_ERROR)
- {
- dlt_log(LOG_ERR,"NWTSegmented: Could not send segment. Aborting.\n");
- break; // Inner loop
- }
- offset += len;
- }while(ptr < data->payload + data->payload_len);
+ char str[255];
+ snprintf(str,254,"NWTSegmented: Error while reading queue: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
+ continue;
+ }
- /* Send the end message */
- DltReturnValue err = dlt_user_trace_network_segmented_end(data->id, data->handle, data->nw_trace_type);
- if(err == DLT_RETURN_BUFFER_FULL || err == DLT_RETURN_ERROR)
- {
- dlt_log(LOG_ERR,"NWTSegmented: Could not send end segment.\n");
- }
+ /* Indicator just to try to flush the buffer */
+ if(data->payload_len == DLT_DELAYED_RESEND_INDICATOR_PATTERN)
+ {
+ // Sleep 100ms, to allow other process to read FIFO
+ usleep(100*1000);
+ if(dlt_user_log_resend_buffer() < 0)
+ {
+ // Requeue if still not empty
+ if ( dlt_user_queue_resend() < 0 )
+ dlt_log(LOG_WARNING, "Failed to queue resending in dlt_user_trace_network_segmented_thread.\n");
+ }
+ free(data);
+ continue;
+ }
- /* Free resources */
- free(data->header);
- free(data->payload);
- free(data);
- }
+ dlt_user_trace_network_segmented_thread_segmenter(data);
+
+ /* Send the end message */
+ DltReturnValue err = dlt_user_trace_network_segmented_end(data->id, data->handle, data->nw_trace_type);
+ if(err == DLT_RETURN_BUFFER_FULL || err == DLT_RETURN_ERROR)
+ {
+ dlt_log(LOG_ERR,"NWTSegmented: Could not send end segment.\n");
+ }
+
+ /* Free resources */
+ free(data->header);
+ free(data->payload);
+ free(data);
+ }
}
+void dlt_user_trace_network_segmented_thread_segmenter(s_segmented_data *data)
+{
+ /* Segment the data and send the chunks */
+ void *ptr = NULL;
+ uint16_t offset = 0;
+ uint16_t sequence = 0;
+ do
+ {
+ uint16_t len = 0;
+ if(offset + DLT_MAX_TRACE_SEGMENT_SIZE > data->payload_len)
+ {
+ len = data->payload_len - offset;
+ }
+ else
+ {
+ len = DLT_MAX_TRACE_SEGMENT_SIZE;
+ }
+ /* If payload size aligns perfectly with segment size, avoid sending empty segment */
+ if(len == 0)
+ {
+ break;
+ }
+
+ ptr = data->payload + offset;
+ DltReturnValue err = dlt_user_trace_network_segmented_segment(data->id, data->handle, data->nw_trace_type, sequence++, len, ptr);
+ if(err == DLT_RETURN_BUFFER_FULL || err == DLT_RETURN_ERROR)
+ {
+ dlt_log(LOG_ERR,"NWTSegmented: Could not send segment. Aborting.\n");
+ break; // loop
+ }
+ offset += len;
+ }while(ptr < data->payload + data->payload_len);
+}
+
+
int dlt_user_trace_network_segmented(DltContext *handle, DltNetworkTraceType nw_trace_type, uint16_t header_len, void *header, uint16_t payload_len, void *payload)
{
/* Send as normal trace if possible */
return -1;
}
+ /* Open queue if it is not open */
+ if(dlt_init_message_queue() < 0)
+ {
+ dlt_log(LOG_ERR, "NWTSegmented: Could not open queue.\n");
+ free(thread_data->header);
+ free(thread_data->payload);
+ free(thread_data);
+
+ return -1;
+ }
+
/* Add to queue */
if(mq_send(dlt_user.dlt_segmented_queue_write_handle,
(char *)&thread_data, sizeof(s_segmented_data *), 1) < 0)
{
+ if(errno == EAGAIN)
+ {
+ dlt_log(LOG_ERR, "NWTSegmented: Queue full. Message discarded.\n");
+ }
free(thread_data->header);
free(thread_data->payload);
- free(thread_data);
- dlt_log(LOG_ERR, "NWTSegmented: Could not write into queue.\n");
- dlt_log(LOG_ERR, strerror(errno));
+ free(thread_data);
+ char str[256];
+ snprintf(str,255,"NWTSegmented: Could not write into queue: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
return -1;
}
+
+ //thread_data will be freed by the receiver function
+ //coverity[leaked_storage]
return 0;
}
/* If truncation is allowed, check if we must do it */
if(allow_truncate > 0 && (header_len+payload_len+sizeof(uint16_t))>DLT_USER_BUF_MAX_SIZE)
{
- int truncated_payload_len = DLT_USER_BUF_MAX_SIZE - header_len - 40; // 40 == overhead bytes
-
/* Identify as truncated */
if(dlt_user_log_write_string(&log, "NWTR") < 0)
{
}
/* Write original size of payload */
- if(dlt_user_log_write_uint(&log, payload_len) < 0)
+ if(dlt_user_log_write_uint16(&log, payload_len) < 0)
{
return -1;
}
+ /**
+ * Calculate maximum avaialble space in sending buffer after headers.
+ */
+
+ int truncated_payload_len = DLT_USER_BUF_MAX_SIZE -
+ log.size - sizeof(uint16_t) - sizeof(uint32_t);
+
/* Write truncated payload */
if (dlt_user_log_write_raw(&log, payload, truncated_payload_len) < 0)
{
return 0;
}
+int dlt_user_queue_resend(void)
+{
+ if(dlt_user.dlt_log_handle < 0)
+ {
+ // Fail silenty. FIFO is not open yet
+ return -1;
+ }
+ /**
+ * Ask segmented thread to try emptying the buffer soon.
+ * This will be freed in dlt_user_trace_network_segmented_thread
+ * */
+ s_segmented_data *resend_data = malloc(sizeof(s_segmented_data));
+
+ if (NULL == resend_data)
+ {
+ return -1;
+ }
+
+ resend_data->payload_len = DLT_DELAYED_RESEND_INDICATOR_PATTERN;
+
+
+
+ /* Open queue if it is not open */
+ if(dlt_init_message_queue() < 0)
+ {
+ dlt_log(LOG_ERR, "NWTSegmented: Could not open queue.\n");
+ free(resend_data);
+ return -1;
+ }
+
+ if(mq_send(dlt_user.dlt_segmented_queue_write_handle, (char *)&resend_data, sizeof(s_segmented_data *), 1) < 0)
+ {
+ char str[255];
+ snprintf(str,254,"Could not request resending.: %s \n",strerror(errno));
+ dlt_log(LOG_CRIT, str);
+ free(resend_data);
+ return -1;
+ }
+ //thread_data will be freed by the receiver function
+ //coverity[leaked_storage]
+ return 0;
+}
+
DltReturnValue dlt_user_log_send_log(DltContextData *log, int mtype)
{
DltMessage msg;
DLT_SEM_FREE();
- /* Ask segmented thread to try emptying the buffer soon. */
- void *indic = (void *)DLT_DELAYED_RESEND_INDICATOR_PATTERN;
- mq_send(dlt_user.dlt_segmented_queue_read_handle, (char *)&indic, sizeof(void *), 1);
+ // Fail silenty if FIFO is not open
+ if(dlt_user_queue_resend() < 0 && dlt_user.dlt_log_handle >= 0)
+ {
+ dlt_log(LOG_WARNING, "dlt_user_log_send_log: Failed to queue resending.\n");
+ }
}
switch (ret)
}
DLT_SEM_FREE();
+
+ if(dlt_user_queue_resend() < 0 && dlt_user.dlt_log_handle >= 0)
+ {
+ dlt_log(LOG_WARNING, "dlt_user_log_send_register_application: Failed to queue resending.\n");
+ }
}
return 0;
}
DLT_SEM_FREE();
+
+ if(dlt_user_queue_resend() < 0 && dlt_user.dlt_log_handle >= 0)
+ {
+ dlt_log(LOG_WARNING, "dlt_user_log_send_register_context: Failed to queue resending.\n");
+ }
}
return 0;
while ((int32_t)(sizeof(DltUserHeader)+offset)<=receiver->bytesRcvd);
/* Check for user header pattern */
- if (dlt_user_check_userheader(userheader)==0)
+ if (dlt_user_check_userheader(userheader)<0 ||
+ dlt_user_check_userheader(userheader)==0)
{
break;
}
/* Delayed injection callback call */
if(delayed_inject_buffer != 0 && delayed_injection_callback.injection_callback != 0) {
delayed_injection_callback.injection_callback(delayed_injection_callback.service_id, delayed_inject_buffer, delayed_inject_data_length);
- free(delayed_inject_buffer);
+ delayed_injection_callback.injection_callback = 0;
+ free(delayed_inject_buffer);
+ delayed_inject_buffer = NULL;
+
}
/* keep not read data in buffer */
int dlt_user_log_resend_buffer(void)
{
int num,count;
- uint8_t buf[DLT_USER_RCVBUF_MAX_SIZE];
int size;
DltReturnValue ret;
{
DLT_SEM_LOCK();
- size = dlt_buffer_copy(&(dlt_user.startup_buffer),buf,sizeof(buf));
+ size = dlt_buffer_copy(&(dlt_user.startup_buffer),dlt_user.resend_buffer,sizeof(dlt_user.resend_buffer));
if (size>0)
{
#ifdef DLT_SHM_ENABLE
- dlt_shm_push(&dlt_user.dlt_shm,buf+sizeof(DltUserHeader),size-sizeof(DltUserHeader),0,0,0,0);
+ dlt_shm_push(&dlt_user.dlt_shm,dlt_user.resend_buffer+sizeof(DltUserHeader),size-sizeof(DltUserHeader),0,0,0,0);
/* log to FIFO */
- ret = dlt_user_log_out3(dlt_user.dlt_log_handle, buf,sizeof(DltUserHeader),0,0,0,0);
+ ret = dlt_user_log_out3(dlt_user.dlt_log_handle, dlt_user.resend_buffer,sizeof(DltUserHeader),0,0,0,0);
#else
/* log to FIFO */
- ret = dlt_user_log_out3(dlt_user.dlt_log_handle, buf,size,0,0,0,0);
+ ret = dlt_user_log_out3(dlt_user.dlt_log_handle, dlt_user.resend_buffer,size,0,0,0,0);
#endif
/* in case of error, keep message in ringbuffer */
for (num=0; num<dlt_user.dlt_ll_ts_num_entries; num++)
{
/* Re-register stored context */
- if ((dlt_user.appID[0]!='\0') && (dlt_user.dlt_ll_ts[num].contextID[0]!='\0') && (dlt_user.dlt_ll_ts))
+ if ((dlt_user.appID[0]!='\0') && (dlt_user.dlt_ll_ts) && (dlt_user.dlt_ll_ts[num].contextID[0]!='\0'))
{
//dlt_set_id(log_new.appID, dlt_user.appID);
dlt_set_id(handle.contextID, dlt_user.dlt_ll_ts[num].contextID);