Added dynamic increasable ringbuffers to user lib and daemon.
authorAlexander Wenzel <Alexander.AW.Wenzel@bmw.de>
Mon, 14 Nov 2011 23:14:39 +0000 (00:14 +0100)
committerAlexander Wenzel <Alexander.AW.Wenzel@bmw.de>
Mon, 14 Nov 2011 23:14:39 +0000 (00:14 +0100)
include/dlt/dlt_common.h
include/dlt/dlt_user.h
src/daemon/dlt-daemon.c
src/daemon/dlt_daemon_common.c
src/daemon/dlt_daemon_common.h
src/lib/dlt_user.c
src/lib/dlt_user_cfg.h
src/shared/dlt_common.c
src/system/dlt-system-log.c

index cb317c6..ba553c4 100755 (executable)
@@ -560,15 +560,22 @@ typedef struct
 
 typedef struct
 {
-       char* shm;      /* pointer to beginning of shared memory */
+       unsigned char* shm;     /* pointer to beginning of shared memory */
        int size;       /* size of data area in shared memory */
-       char* mem;      /* pointer to data area in shared memory */     
+       unsigned char* mem;     /* pointer to data area in shared memory */     
        
     uint32_t    min_size;  /**< Minimum size of buffer */
     uint32_t    max_size;  /**< Maximum size of buffer */
     uint32_t    step_size; /**< Step size of buffer */
 } DltBuffer;
 
+typedef struct
+{
+       int write;
+       int read;
+       int count;      
+} DltBufferHead;
+
 #define DLT_BUFFER_HEAD        "SHM"
 
 typedef struct
@@ -980,12 +987,6 @@ extern "C"
        int dlt_buffer_get_used_size(DltBuffer *buf);
        int dlt_buffer_get_message_count(DltBuffer *buf);
 
-       int dlt_buffer_get(DltBuffer *buf,unsigned char *data, int max_size,int delete);
-       int dlt_buffer_reset(DltBuffer *buf);
-       void dlt_buffer_write_block(DltBuffer *buf,int *write, const unsigned char *data,unsigned int size);
-       void dlt_buffer_read_block(DltBuffer *buf,int *read,unsigned char *data,unsigned int size);     
-
-
     /**
      * Initialize ringbuffer of with a maximum size of size
      * @param dltbuf Pointer to ringbuffer structure
index db5b954..dbc40a2 100755 (executable)
@@ -240,7 +240,8 @@ typedef struct
 
     int8_t log_state;                                    /**< Log state of external connection: 1 client connected, 0 not connected, -1 unknown */
 
-    DltRingBuffer rbuf;                   /**< Ring-buffer for buffering messages during startup and missing connection */
+    //DltRingBuffer rbuf;                 
+       DltBuffer startup_buffer; /**< Ring-buffer for buffering messages during startup and missing connection */
     
     DltShm dlt_shm;
 } DltUser;
index f2ba0cb..dd18d4b 100755 (executable)
@@ -1171,7 +1171,7 @@ int dlt_daemon_process_user_messages(DltDaemon *daemon, DltDaemonLocal *daemon_l
     }
 
     /* read data from FIFO */
-    if (dlt_receiver_receive_fd(&(daemon_local->receiver))<=0)
+    if (dlt_receiver_receive_fd(&(daemon_local->receiver))<0)
     {
         dlt_log(LOG_ERR, "dlt_receiver_receive_fd() for user messages failed!\n");
         return -1;
@@ -1855,7 +1855,7 @@ int dlt_daemon_process_user_message_log(DltDaemon *daemon, DltDaemonLocal *daemo
             /* Message was not sent to client, so store it in client ringbuffer */
             if (sent==0)
             {
-                if (dlt_ringbuffer_put3(&(daemon->client_ringbuffer),
+                if (dlt_buffer_push3(&(daemon->client_ringbuffer),
                                     daemon_local->msg.headerbuffer+sizeof(DltStorageHeader),daemon_local->msg.headersize-sizeof(DltStorageHeader),
                                     daemon_local->msg.databuffer,daemon_local->msg.datasize,
                                     0, 0
@@ -2182,8 +2182,8 @@ int dlt_daemon_process_user_message_log_mode(DltDaemon *daemon, DltDaemonLocal *
 
 int dlt_daemon_send_ringbuffer_to_client(DltDaemon *daemon, DltDaemonLocal *daemon_local, int verbose)
 {
-    static uint8_t data[DLT_DAEMON_RINGBUFFER_SIZE];
-    size_t length=0;
+    static uint8_t data[DLT_DAEMON_RCVBUFSIZE];
+    int length;
     int j, third_value;
     ssize_t ret;
 
@@ -2196,7 +2196,7 @@ int dlt_daemon_send_ringbuffer_to_client(DltDaemon *daemon, DltDaemonLocal *daem
     }
 
        /* Attention: If the message can't be send at this time, it will be silently discarded. */
-    while ((dlt_ringbuffer_get(&(daemon->client_ringbuffer), data, &length ))!=-1)
+    while ((length = dlt_buffer_pull(&(daemon->client_ringbuffer), data, sizeof(data) )) > 0)
     {
         /* look if TCP connection to client is available */
         for (j = 0; j <= daemon_local->fdmax; j++)
@@ -2241,6 +2241,7 @@ int dlt_daemon_send_ringbuffer_to_client(DltDaemon *daemon, DltDaemonLocal *daem
                 }
             } /* if */
         } /* for */
+        length = sizeof(data);
     }
 
     return 0;
index aaed7a2..1de6aea 100755 (executable)
@@ -188,7 +188,7 @@ int dlt_daemon_init(DltDaemon *daemon,const char *runtime_directory, int verbose
     dlt_set_id(daemon->ecuid,"");
 
     /* initialize ring buffer for client connection */
-    if (dlt_ringbuffer_init(&(daemon->client_ringbuffer), DLT_DAEMON_RINGBUFFER_SIZE)==-1)
+    if (dlt_buffer_init_dynamic(&(daemon->client_ringbuffer), DLT_DAEMON_RINGBUFFER_MIN_SIZE,DLT_DAEMON_RINGBUFFER_MAX_SIZE,DLT_DAEMON_RINGBUFFER_STEP_SIZE)==-1)
     {
        return -1;
     }
@@ -217,6 +217,9 @@ int dlt_daemon_free(DltDaemon *daemon,int verbose)
                return -1;
     }
 
+       /* free ringbuffer */
+       dlt_buffer_free_dynamic(&(daemon->client_ringbuffer));
+
     return 0;
 }
 
@@ -2145,7 +2148,7 @@ void dlt_daemon_control_send_control_message( int sock, DltDaemon *daemon, DltMe
     else
     {
         /* Store message in history buffer */
-        if (dlt_ringbuffer_put3(&(daemon->client_ringbuffer),
+        if (dlt_buffer_push3(&(daemon->client_ringbuffer),
                             msg->headerbuffer+sizeof(DltStorageHeader),msg->headersize-sizeof(DltStorageHeader),
                             msg->databuffer,msg->datasize,
                             0, 0
index 17bc32f..1870295 100755 (executable)
@@ -96,7 +96,9 @@
 extern "C" {\r
 #endif\r
 \r
-#define DLT_DAEMON_RINGBUFFER_SIZE 100000 /**< Ring buffer size for storing log messages while no client is connected */\r
+#define DLT_DAEMON_RINGBUFFER_MIN_SIZE  100000 /**< Ring buffer size for storing log messages while no client is connected */\r
+#define DLT_DAEMON_RINGBUFFER_MAX_SIZE  500000 /**< Ring buffer size for storing log messages while no client is connected */\r
+#define DLT_DAEMON_RINGBUFFER_STEP_SIZE 100000 /**< Ring buffer size for storing log messages while no client is connected */\r
 \r
 #define DLT_DAEMON_STORE_TO_BUFFER -2   /**< Constant value to identify the command "store to buffer" */\r
 \r
@@ -149,7 +151,7 @@ typedef struct
        char ecuid[DLT_ID_SIZE];       /**< ECU ID of daemon */\r
        int sendserialheader;          /**< 1: send serial header; 0 don't send serial header */\r
        int timingpackets;              /**< 1: send continous timing packets; 0 don't send continous timing packets */\r
-       DltRingBuffer client_ringbuffer; /**< Ring-buffer for storing received logs while no client connection is available */\r
+       DltBuffer client_ringbuffer; /**< Ring-buffer for storing received logs while no client connection is available */\r
        char runtime_application_cfg[256]; /**< Path and filename of persistent application configuration */\r
        char runtime_context_cfg[256]; /**< Path and filename of persistent context configuration */\r
        char runtime_configuration[256]; /**< Path and filename of persistent configuration */\r
index eac0215..178df18 100755 (executable)
@@ -122,6 +122,7 @@ static int dlt_send_app_ll_ts_limit(const char *appid, DltLogLevelType loglevel,
 static int dlt_user_log_send_log_mode(DltUserLogMode mode);
 static int dlt_user_print_msg(DltMessage *msg, DltContextData *log);
 static int dlt_user_log_check_user_message(void);
+static int dlt_user_log_resend_buffer(void);
 static void dlt_user_log_reattach_to_daemon(void);
 static int dlt_user_log_send_overflow(void);
 
@@ -311,7 +312,7 @@ int dlt_init_common(void)
     dlt_user.dlt_ll_ts_max_num_entries = 0;
     dlt_user.dlt_ll_ts_num_entries = 0;
 
-    if (dlt_ringbuffer_init(&(dlt_user.rbuf), DLT_USER_RINGBUFFER_SIZE)==-1)
+    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;
         return -1;
@@ -375,7 +376,7 @@ int dlt_free(void)
     dlt_receiver_free(&(dlt_user.receiver));
 
        /* Ignore return value */
-    dlt_ringbuffer_free(&(dlt_user.rbuf));
+    dlt_buffer_free_dynamic(&(dlt_user.startup_buffer));
 
     if (dlt_user.dlt_ll_ts)
     {
@@ -879,7 +880,7 @@ int dlt_forward_msg(void *msgdata,size_t size)
         {
             DLT_SEM_LOCK();
 
-            if (dlt_ringbuffer_put3(&(dlt_user.rbuf),
+            if (dlt_buffer_push3(&(dlt_user.startup_buffer),
                                 &(userheader), sizeof(DltUserHeader),
                                  msgdata, size, 0, 0)==-1)
                        {
@@ -2020,7 +2021,7 @@ int dlt_user_log_send_log(DltContextData *log, int mtype)
     DltUserHeader userheader;
     int32_t len;
 
-    DltReturnValue ret;
+    DltReturnValue ret = 0;
 
     if (log==0)
     {
@@ -2186,29 +2187,38 @@ int dlt_user_log_send_log(DltContextData *log, int mtype)
             }
         }
 
+               /* try to resent old data first */
+               ret = 0;
+               if(dlt_user.dlt_log_handle!=-1)
+                       ret = dlt_user_log_resend_buffer();
+               if(ret==0) 
+               {
+                       /* resend ok or nothing to resent */
 #ifdef DLT_SHM_ENABLE
-               dlt_shm_push(&dlt_user.dlt_shm,msg.headerbuffer+sizeof(DltStorageHeader), msg.headersize-sizeof(DltStorageHeader),
-                                                                       log->buffer, log->size,0,0);                   
-
-        /* log to FIFO */
-        ret = dlt_user_log_out3(dlt_user.dlt_log_handle,
-                                &(userheader), sizeof(DltUserHeader),
-                                0, 0,
-                                0, 0);
+                       if(dlt_user.dlt_log_handle!=-1)
+                               dlt_shm_push(&dlt_user.dlt_shm,msg.headerbuffer+sizeof(DltStorageHeader), msg.headersize-sizeof(DltStorageHeader),
+                                                                                       log->buffer, log->size,0,0);                   
+
+                       /* log to FIFO */
+                       ret = dlt_user_log_out3(dlt_user.dlt_log_handle,
+                                                                       &(userheader), sizeof(DltUserHeader),
+                                                                       0, 0,
+                                                                       0, 0);
 #else
-        /* log to FIFO */
-        ret = dlt_user_log_out3(dlt_user.dlt_log_handle,
-                                &(userheader), sizeof(DltUserHeader),
-                                msg.headerbuffer+sizeof(DltStorageHeader), msg.headersize-sizeof(DltStorageHeader),
-                                log->buffer, log->size);
-
+                       /* log to FIFO */
+                       ret = dlt_user_log_out3(dlt_user.dlt_log_handle,
+                                                                       &(userheader), sizeof(DltUserHeader),
+                                                                       msg.headerbuffer+sizeof(DltStorageHeader), msg.headersize-sizeof(DltStorageHeader),
+                                                                       log->buffer, log->size);                
 #endif                 
+               }
+               
         /* store message in ringbuffer, if an error has occured */
         if (ret!=DLT_RETURN_OK)
         {
             DLT_SEM_LOCK();
 
-            if (dlt_ringbuffer_put3(&(dlt_user.rbuf),
+            if (dlt_buffer_push3(&(dlt_user.startup_buffer),
                                 &(userheader), sizeof(DltUserHeader),
                                 msg.headerbuffer+sizeof(DltStorageHeader), msg.headersize-sizeof(DltStorageHeader),
                                 log->buffer, log->size)==-1)
@@ -2755,19 +2765,77 @@ int dlt_user_log_check_user_message(void)
         } /* while receive */
     } /* if */
 
-    return 0;
+    return DLT_RETURN_OK;
 }
 
-void dlt_user_log_reattach_to_daemon(void)
+int dlt_user_log_resend_buffer(void)
 {
-    int num, count, reregistered=0;
+       int num,count;
+    uint8_t buf[DLT_USER_RCVBUF_MAX_SIZE];
+    int size;
+       DltReturnValue ret;
+       
+       /* Send content of ringbuffer */
+       DLT_SEM_LOCK();
+       count = dlt_buffer_get_message_count(&(dlt_user.startup_buffer));
+       DLT_SEM_FREE();
 
-    uint8_t buf[DLT_USER_RINGBUFFER_SIZE];
-    size_t size;
+       for (num=0;num<count;num++)
+       {
+
+               DLT_SEM_LOCK();
+               size = dlt_buffer_copy(&(dlt_user.startup_buffer),buf,sizeof(buf));
+
+               if (size>0)
+               {
+#ifdef DLT_SHM_ENABLE                                          
+                       dlt_shm_push(&dlt_user.dlt_shm,buf+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);
+#else
+                       /* log to FIFO */
+                       ret = dlt_user_log_out3(dlt_user.dlt_log_handle, buf,size,0,0,0,0);
+#endif
+
+                       /* in case of error, keep message in ringbuffer */                        
+                       if (ret==DLT_RETURN_OK)
+                       {
+                               dlt_buffer_remove(&(dlt_user.startup_buffer));
+                               /*
+                               DLT_SEM_LOCK();
+                               if (dlt_buffer_push(&(dlt_user.startup_buffer), buf, size)==-1)
+                               {
+                                       dlt_log(LOG_ERR,"Error pushing back message to history buffer. Message discarded.\n");
+                               }
+                               DLT_SEM_FREE();
+
+                               // In case of: data could not be written, set overflow flag
+                               if (ret==DLT_RETURN_PIPE_FULL)
+                               {
+                                       dlt_user.overflow = 1;
+                               }
+                               */
+                       }
+                       else
+                       {
+                               /* keep message in ringbuffer */   
+                               DLT_SEM_FREE();
+                               return -1;
+                       }
+               }
+               DLT_SEM_FREE();
+       }
+       
+       return 0;
+}
+
+void dlt_user_log_reattach_to_daemon(void)
+{
+    int num,reregistered=0;
 
        DltContext handle;
        DltContextData log_new;
-       DltReturnValue ret;
 
     if (dlt_user.dlt_log_handle<0)
     {
@@ -2828,49 +2896,7 @@ void dlt_user_log_reattach_to_daemon(void)
 
             if (reregistered==1)
             {
-                /* Send content of ringbuffer */
-                DLT_SEM_LOCK();
-                count = dlt_user.rbuf.count;
-                DLT_SEM_FREE();
-
-                for (num=0;num<count;num++)
-                {
-
-                    DLT_SEM_LOCK();
-                    dlt_ringbuffer_get(&(dlt_user.rbuf),buf,&size);
-                    DLT_SEM_FREE();
-
-                    if (size>0)
-                    {
-#ifdef DLT_SHM_ENABLE                                          
-                                               dlt_shm_push(&dlt_user.dlt_shm,buf+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);
-#else
-                        /* log to FIFO */
-                        ret = dlt_user_log_out3(dlt_user.dlt_log_handle, buf,size,0,0,0,0);
-#endif
-
-                        /* in case of error, push message back to ringbuffer */                        
-                        if (ret!=DLT_RETURN_OK)
-                        {
-                            DLT_SEM_LOCK();
-                            if (dlt_ringbuffer_put(&(dlt_user.rbuf), buf, size)==-1)
-                            {
-                                                               dlt_log(LOG_ERR,"Error pushing back message to history buffer. Message discarded.\n");
-                            }
-                            DLT_SEM_FREE();
-
-                            /* In case of: data could not be written, set overflow flag */
-                            if (ret==DLT_RETURN_PIPE_FULL)
-                            {
-                                dlt_user.overflow = 1;
-                            }
-                        }
-                    }
-
-                }
+                               dlt_user_log_resend_buffer();
             }
         }
     }
@@ -2899,8 +2925,13 @@ int dlt_user_log_send_overflow(void)
 
 int dlt_user_check_buffer(int *total_size, int *used_size)
 {
+#ifdef DLT_SHM_ENABLE
        *total_size = dlt_shm_get_total_size(&(dlt_user.dlt_shm));
        *used_size = dlt_shm_get_used_size(&(dlt_user.dlt_shm));
+#else
+       *total_size = dlt_buffer_get_total_size(&(dlt_user.startup_buffer));
+       *used_size = dlt_buffer_get_used_size(&(dlt_user.startup_buffer));
+#endif
        
        return 0; /* ok */
 }
index 5b1e71e..e3bb8a3 100755 (executable)
@@ -88,7 +88,9 @@
 #define DLT_USER_RCVBUF_MAX_SIZE 10024 \r
 \r
 /* Size of ring buffer */      \r
-#define DLT_USER_RINGBUFFER_SIZE 10024       \r
+#define DLT_USER_RINGBUFFER_MIN_SIZE  10000       \r
+#define DLT_USER_RINGBUFFER_MAX_SIZE  60000       \r
+#define DLT_USER_RINGBUFFER_STEP_SIZE 10000       \r
 \r
 /* Temporary buffer length */\r
 #define DLT_USER_BUFFER_LENGTH               255\r
index 8e52265..f744702 100755 (executable)
@@ -132,6 +132,14 @@ static char *service_id[] = {"","set_log_level","set_trace_status","get_log_info
                             };
 static char *return_type[] = {"ok","not_supported","error","","","","","","no_matching_context_id"};
 
+/* internal function definitions */
+int dlt_buffer_get(DltBuffer *buf,unsigned char *data, int max_size,int delete);
+int dlt_buffer_reset(DltBuffer *buf);
+int dlt_buffer_increase_size(DltBuffer *buf);
+int dlt_buffer_minimize_size(DltBuffer *buf);
+void dlt_buffer_write_block(DltBuffer *buf,int *write, const unsigned char *data,unsigned int size);
+void dlt_buffer_read_block(DltBuffer *buf,int *read,unsigned char *data,unsigned int size);    
+
 void dlt_print_hex(uint8_t *ptr,int size)
 {
     int num;
@@ -2286,6 +2294,7 @@ int dlt_check_storageheader(DltStorageHeader *storageheader)
 int dlt_buffer_init_static_server(DltBuffer *buf, const unsigned char *ptr, uint32_t size)
 {
        char str[256];
+       DltBufferHead *head;
 
        // Init parameters
        buf->shm = ptr;
@@ -2294,11 +2303,12 @@ int dlt_buffer_init_static_server(DltBuffer *buf, const unsigned char *ptr, uint
        buf->step_size = 0;
        
        // Init pointers
-    ((int*)(buf->shm))[0] = 0;  // pointer to write memory  
-    ((int*)(buf->shm))[1] = 0;  // pointer to read memory
-    ((int*)(buf->shm))[2] = 0;  // number of packets
-    buf->mem = (char*)(&(((int*)(buf->shm))[3]));
-    buf->size = size - (buf->mem - buf->shm);
+       head = (DltBufferHead*)buf->shm;
+       head->read = 0;
+       head->write = 0;
+       head->count = 0;
+    buf->mem = (char*)(buf->shm + sizeof(DltBufferHead));
+       buf->size = buf->min_size - sizeof(DltBufferHead);
 
        // clear memory
        memset(buf->mem,0,buf->size);
@@ -2312,6 +2322,7 @@ int dlt_buffer_init_static_server(DltBuffer *buf, const unsigned char *ptr, uint
 int dlt_buffer_init_static_client(DltBuffer *buf, const unsigned char *ptr, uint32_t size)
 {
        char str[256];
+       DltBufferHead *head;
 
        // Init parameters
        buf->shm = ptr;
@@ -2320,8 +2331,8 @@ int dlt_buffer_init_static_client(DltBuffer *buf, const unsigned char *ptr, uint
        buf->step_size = 0;
        
        // Init pointers
-    buf->mem = (char*)(&(((int*)(buf->shm))[3]));
-    buf->size = size - (buf->mem - buf->shm);
+    buf->mem = (char*)(buf->shm + sizeof(DltBufferHead));
+    buf->size = buf->min_size - sizeof(DltBufferHead);
 
        snprintf(str,sizeof(str),"Buffer: Size %d\n",buf->size);
        dlt_log(LOG_INFO, str);
@@ -2332,6 +2343,7 @@ int dlt_buffer_init_static_client(DltBuffer *buf, const unsigned char *ptr, uint
 int dlt_buffer_init_dynamic(DltBuffer *buf, uint32_t min_size, uint32_t max_size,uint32_t step_size)
 {
        char str[256];
+       DltBufferHead *head;
 
        // Init parameters
        buf->min_size = min_size;
@@ -2339,7 +2351,7 @@ int dlt_buffer_init_dynamic(DltBuffer *buf, uint32_t min_size, uint32_t max_size
        buf->step_size = step_size;
 
        // allocat memory
-       buf->shm = malloc(buf->min_size+3*sizeof(int));
+       buf->shm = malloc(buf->min_size);
        if(buf->shm == NULL) {
                snprintf(str,sizeof(str),"Buffer: Cannot allocate %d bytes\n",buf->min_size);
                dlt_log(LOG_EMERG, str);
@@ -2347,11 +2359,12 @@ int dlt_buffer_init_dynamic(DltBuffer *buf, uint32_t min_size, uint32_t max_size
        }
        
        // Init pointers
-    ((int*)(buf->shm))[0] = 0;  // pointer to write memory  
-    ((int*)(buf->shm))[1] = 0;  // pointer to read memory
-    ((int*)(buf->shm))[2] = 0;  // number of packets
-    buf->mem = (char*)(&(((int*)(buf->shm))[3]));
-    buf->size = buf->min_size - 3 * sizeof(int);
+       head = (DltBufferHead*)buf->shm;
+       head->read = 0;
+       head->write = 0;
+       head->count = 0;
+    buf->mem = (char*)(buf->shm + sizeof(DltBufferHead));
+    buf->size = buf->min_size - sizeof(DltBufferHead);
 
        // clear memory
        memset(buf->mem,0,buf->size);
@@ -2416,6 +2429,101 @@ void dlt_buffer_read_block(DltBuffer *buf,int *read,unsigned char *data,unsigned
        }       
 }      
 
+int dlt_buffer_increase_size(DltBuffer *buf)
+{
+       DltBufferHead *head,*new_head;
+       unsigned char *new_ptr;
+
+       /* check size */
+       if(buf->step_size==0) {
+               /* cannot increase size */
+               return -1;
+       }
+
+       /* check size */
+       if((buf->size + sizeof(DltBufferHead) + buf->step_size) > buf->max_size) {
+               /* max size reached, do not increase */
+               return -1;
+       }
+
+       /* allocate new buffer */
+       new_ptr = malloc(buf->size + sizeof(DltBufferHead) + buf->step_size);
+       if(new_ptr == NULL) {
+               snprintf(str,sizeof(str),"Buffer: Cannot increase size because allocate %d bytes failed\n",buf->min_size);
+               dlt_log(LOG_WARNING, str);
+               return -1;
+       }
+               
+       /* copy data */
+       head = (DltBufferHead*)buf->shm;
+       new_head = (DltBufferHead*)new_ptr;
+       if(head->read < head->write) {
+               memcpy(new_ptr+sizeof(DltBufferHead) , buf->mem+head->read , head->write-head->read);
+               new_head->read = 0;     
+               new_head->write = head->write-head->read;       
+               new_head->count = head->count;  
+       }
+       else {
+               memcpy(new_ptr+sizeof(DltBufferHead) , buf->mem+head->read , buf->size-head->read);
+               memcpy(new_ptr+sizeof(DltBufferHead)+buf->size-head->read , buf->mem , head->write);
+               new_head->read = 0;     
+               new_head->write = buf->size-head->read+head->write;     
+               new_head->count = head->count;                  
+       }
+       
+       /* free old data */
+       free(buf->shm);
+       
+       /* update data */
+       buf->shm = new_ptr;
+       buf->mem = new_ptr+sizeof(DltBufferHead);
+       buf->size += buf->step_size;
+       
+       snprintf(str,sizeof(str),"Buffer: Size increased to %d bytes\n",buf->size+sizeof(DltBufferHead));
+       dlt_log(LOG_INFO, str);
+
+       return 0; // OK         
+}
+
+int dlt_buffer_minimize_size(DltBuffer *buf)
+{
+       unsigned char *new_ptr;
+
+       if((buf->size + sizeof(DltBufferHead)) == buf->min_size)
+       {
+               /* already minimized */
+               return 0;
+       }
+
+       /* allocate new buffer */
+       new_ptr = malloc(buf->min_size);
+       if(new_ptr == NULL) {
+               snprintf(str,sizeof(str),"Buffer: Cannot set to min size of %d bytes\n",buf->min_size);
+               dlt_log(LOG_WARNING, str);
+               return -1;
+       }
+
+       /* free old data */
+       free(buf->shm);
+       
+       /* update data */
+       buf->shm = new_ptr;
+       buf->mem = new_ptr+sizeof(DltBufferHead);
+       buf->size = buf->min_size - sizeof(DltBufferHead);
+
+       /* reset pointers and counters */       
+       ((int*)(buf->shm))[0] = 0;  // pointer to write memory  
+       ((int*)(buf->shm))[1] = 0;  // pointer to read memory
+       ((int*)(buf->shm))[2] = 0;  // number of packets
+
+       // clear memory
+       memset(buf->mem,0,buf->size);
+
+       dlt_log(LOG_INFO,"Buffer: Buffer minimized.\n");
+
+       return 0; /* OK */      
+}
+
 int dlt_buffer_reset(DltBuffer *buf)
 {
        dlt_log(LOG_ERR,"Buffer: Buffer reset triggered.\n");
@@ -2468,8 +2576,15 @@ int dlt_buffer_push3(DltBuffer *buf,const unsigned char *data1,unsigned int size
        
        // check size
        if(free_size < (sizeof(DltBufferBlockHead)+size1+size2+size3)) {
-               dlt_log(LOG_ERR,"Buffer: Buffer is full\n");
-               return -1; // ERROR
+               // try to increase size if possible
+               if(dlt_buffer_increase_size(buf)) {
+                       /* increase size is not possible */
+                       dlt_log(LOG_ERR,"Buffer: Buffer is full\n");
+                       return -1; // ERROR
+               }
+               // update pointers
+               write = ((int*)(buf->shm))[0];
+               read = ((int*)(buf->shm))[1];
        }
 
        // set header
@@ -2592,6 +2707,12 @@ int dlt_buffer_get(DltBuffer *buf,unsigned char *data, int max_size,int delete)
        }
        if(delete) {
                ((int*)(buf->shm))[2] -= 1; // decrease counter
+       
+               if(((int*)(buf->shm))[2] == 0)
+               {
+                       // try to minimize size
+                       dlt_buffer_minimize_size(buf);
+               }
        }
        
        return head.size; // OK 
@@ -2644,7 +2765,7 @@ void dlt_buffer_status(DltBuffer *buf)
 
 int dlt_buffer_get_total_size(DltBuffer *buf)
 {
-       return buf->size;       
+       return buf->max_size;   
 }
 
 int dlt_buffer_get_used_size(DltBuffer *buf)
index 6a76221..cf2b495 100644 (file)
@@ -181,11 +181,9 @@ void dlt_system_filetransfer_run(DltSystemOptions *options,DltSystemRuntime *run
                                printf("Error: dlt_user_log_file_data\n");
                                return;
                        }                       
-#ifdef DLT_SHM_ENABLE
                        /* wait sending next package if more than 50% of buffer used */
                        dlt_user_check_buffer(&total_size, &used_size);
                        if((total_size - used_size) < (total_size/2))
-#endif
                                break;
                }
                if(runtime->filetransferLastSentPackage==runtime->filetransferCountPackages) {