From c7d5f90ba982bc3dba3aa356c70ba5ac8863d699 Mon Sep 17 00:00:00 2001
From: Jan Breuer <jan.breuer@jaybee.cz>
Date: 周日, 24 4月 2016 20:20:50 +0800
Subject: [PATCH] Fix OUR_strndup, optimize non USE_DEVICE_DEPENDENT_ERROR_INFORMATION configuration

---
 libscpi/inc/scpi/types.h         |    4 +
 examples/test-parser/main.c      |    3 
 libscpi/src/parser.c             |   34 ++++++++---
 examples/test-tcp/main.c         |    3 
 libscpi/inc/scpi/config.h        |    8 +-
 libscpi/src/utils_private.h      |    7 +-
 libscpi/src/error.c              |   15 +++--
 libscpi/inc/scpi/parser.h        |    6 +
 libscpi/test/test_parser.c       |   10 ++
 examples/test-interactive/main.c |    3 
 examples/test-tcp-srq/main.c     |    3 
 libscpi/src/utils.c              |   31 ++++++++-
 12 files changed, 88 insertions(+), 39 deletions(-)

diff --git a/examples/test-interactive/main.c b/examples/test-interactive/main.c
index e6e5763..c8cb4d1 100644
--- a/examples/test-interactive/main.c
+++ b/examples/test-interactive/main.c
@@ -94,8 +94,7 @@
             scpi_units_def,
             SCPI_IDN1, SCPI_IDN2, SCPI_IDN3, SCPI_IDN4,
             scpi_input_buffer, SCPI_INPUT_BUFFER_LENGTH,
-            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE,
-            NULL, 0);
+            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE);
 
     //printf("%.*s %s\r\n",  3, "asdadasdasdasdas", "b");
     printf("SCPI Interactive demo\r\n");
diff --git a/examples/test-parser/main.c b/examples/test-parser/main.c
index e72b8af..e5badb1 100644
--- a/examples/test-parser/main.c
+++ b/examples/test-parser/main.c
@@ -96,8 +96,7 @@
             scpi_units_def,
             SCPI_IDN1, SCPI_IDN2, SCPI_IDN3, SCPI_IDN4,
             scpi_input_buffer, SCPI_INPUT_BUFFER_LENGTH,
-            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE,
-            NULL, 0);
+            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE);
 
 #define TEST_SCPI_INPUT(cmd)    result = SCPI_Input(&scpi_context, cmd, strlen(cmd))
 
diff --git a/examples/test-tcp-srq/main.c b/examples/test-tcp-srq/main.c
index af81109..095fdb8 100644
--- a/examples/test-tcp-srq/main.c
+++ b/examples/test-tcp-srq/main.c
@@ -290,8 +290,7 @@
             scpi_units_def,
             SCPI_IDN1, SCPI_IDN2, SCPI_IDN3, SCPI_IDN4,
             scpi_input_buffer, SCPI_INPUT_BUFFER_LENGTH,
-            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE,
-            NULL, 0);
+            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE);
     scpi_context.user_context = &user_data;
 
     user_data.io_listen = createServer(5025);
diff --git a/examples/test-tcp/main.c b/examples/test-tcp/main.c
index bab7bf2..f1971c2 100644
--- a/examples/test-tcp/main.c
+++ b/examples/test-tcp/main.c
@@ -188,8 +188,7 @@
             scpi_units_def,
             SCPI_IDN1, SCPI_IDN2, SCPI_IDN3, SCPI_IDN4,
             scpi_input_buffer, SCPI_INPUT_BUFFER_LENGTH,
-            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE,
-            NULL, 0);
+            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE);
 
     listenfd = createServer(5025);
 
diff --git a/libscpi/inc/scpi/config.h b/libscpi/inc/scpi/config.h
index ee07954..712b706 100644
--- a/libscpi/inc/scpi/config.h
+++ b/libscpi/inc/scpi/config.h
@@ -271,14 +271,14 @@
 #define SCPIDEFINE_free(h, s, r)                        free((s))
 #else
 #define SCPIDEFINE_DESCRIPTION_MAX_PARTS                3
-#define SCPIDEFINE_strndup(h, s, l)                     OUR_strndup((h), (s), (l))
-#define SCPIDEFINE_free(h, s, r)                        OUR_free((h), (s), (r))
-#define SCPIDEFINE_get_parts(h, s, l1, s2, l2)          OUR_get_parts((h), (s), (l1), (s2), (l2))
+#define SCPIDEFINE_strndup(h, s, l)                     scpiheap_strndup((h), (s), (l))
+#define SCPIDEFINE_free(h, s, r)                        scpiheap_free((h), (s), (r))
+#define SCPIDEFINE_get_parts(h, s, l1, s2, l2)          scpiheap_get_parts((h), (s), (l1), (s2), (l2))
 #endif
 #else
 #define SCPIDEFINE_DESCRIPTION_MAX_PARTS                1
 #define SCPIDEFINE_strdup(h, s, l)                      NULL
-#define SCPIDEFINE_free(h, s, r)                        (void)
+#define SCPIDEFINE_free(h, s, r)
 #endif
 
 #ifdef	__cplusplus
diff --git a/libscpi/inc/scpi/parser.h b/libscpi/inc/scpi/parser.h
index 8e782e9..2f00c82 100644
--- a/libscpi/inc/scpi/parser.h
+++ b/libscpi/inc/scpi/parser.h
@@ -49,8 +49,10 @@
             const scpi_unit_def_t * units,
             const char * idn1, const char * idn2, const char * idn3, const char * idn4,
             char * input_buffer, size_t input_buffer_length, 
-            scpi_error_t * error_queue_data, int16_t error_queue_size,
-            char * error_info_heap, size_t error_info_heap_length);
+            scpi_error_t * error_queue_data, int16_t error_queue_size);
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
+    void SCPI_InitHeap(scpi_t * context, char * error_info_heap, size_t error_info_heap_length);
+#endif
 
     scpi_bool_t SCPI_Input(scpi_t * context, const char * data, int len);
     scpi_bool_t SCPI_Parse(scpi_t * context, char * data, int len);
diff --git a/libscpi/inc/scpi/types.h b/libscpi/inc/scpi/types.h
index a9f3cfe..c8ddf2e 100644
--- a/libscpi/inc/scpi/types.h
+++ b/libscpi/inc/scpi/types.h
@@ -212,7 +212,9 @@
 
     struct _scpi_error_t {
         int16_t error_code;
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION
         char * device_dependent_info;
+#endif
     };
     typedef struct _scpi_error_t scpi_error_t;
 
@@ -365,7 +367,9 @@
         int_fast16_t input_count;
         scpi_bool_t cmd_error;
         scpi_fifo_t error_queue;
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
         scpi_error_info_heap_t error_info_heap;
+#endif
         scpi_reg_val_t registers[SCPI_REG_COUNT];
         const scpi_unit_def_t * units;
         void * user_context;
diff --git a/libscpi/src/error.c b/libscpi/src/error.c
index 3b9ca01..e07ced3 100644
--- a/libscpi/src/error.c
+++ b/libscpi/src/error.c
@@ -41,6 +41,12 @@
 #include "scpi/error.h"
 #include "fifo_private.h"
 
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION
+#define SCPI_ERROR_SETVAL(e, c, i) do { (e)->error_code = (c); (e)->device_dependent_info = (i); } while(0)
+#else
+#define SCPI_ERROR_SETVAL(e, c, i) do { (e)->error_code = (c); } while(0)
+#endif
+
 /**
  * Initialize error queue
  * @param context - scpi context
@@ -100,8 +106,7 @@
  */
 scpi_bool_t SCPI_ErrorPop(scpi_t * context, scpi_error_t * error) {
     if (!error || !context) return FALSE;
-    error->error_code = 0;
-    error->device_dependent_info = NULL;
+    SCPI_ERROR_SETVAL(error, 0, NULL);
     fifo_remove(&context->error_queue, error);
 
     SCPI_ErrorEmitEmpty(context);
@@ -124,13 +129,11 @@
 
 static scpi_bool_t SCPI_ErrorAddInternal(scpi_t * context, int16_t err, char * info) {
     scpi_error_t error_value;
-    error_value.error_code = err;
-    error_value.device_dependent_info = info;
+    SCPI_ERROR_SETVAL(&error_value, err, info);
     if (!fifo_add(&context->error_queue, &error_value)) {
         fifo_remove_last(&context->error_queue, &error_value);
         SCPIDEFINE_free(&context->error_info_heap, error_value.device_dependent_info, false);
-        error_value.error_code = SCPI_ERROR_QUEUE_OVERFLOW;
-        error_value.device_dependent_info = NULL;
+        SCPI_ERROR_SETVAL(&error_value, SCPI_ERROR_QUEUE_OVERFLOW, NULL);
         fifo_add(&context->error_queue, &error_value);
         return FALSE;
     }
diff --git a/libscpi/src/parser.c b/libscpi/src/parser.c
index 6ced497..af37b01 100644
--- a/libscpi/src/parser.c
+++ b/libscpi/src/parser.c
@@ -246,9 +246,17 @@
 /**
  * Initialize SCPI context structure
  * @param context
- * @param command_list
- * @param buffer
+ * @param commands
  * @param interface
+ * @param units
+ * @param idn1
+ * @param idn2
+ * @param idn3
+ * @param idn4
+ * @param input_buffer
+ * @param input_buffer_length
+ * @param error_queue_data
+ * @param error_queue_size
  */
 void SCPI_Init(scpi_t * context,
         const scpi_command_t * commands,
@@ -256,8 +264,7 @@
         const scpi_unit_def_t * units,
         const char * idn1, const char * idn2, const char * idn3, const char * idn4,
         char * input_buffer, size_t input_buffer_length,
-        scpi_error_t * error_queue_data, int16_t error_queue_size,
-        char * error_info_heap, size_t error_info_heap_length) {
+        scpi_error_t * error_queue_data, int16_t error_queue_size) {
     memset(context, 0, sizeof (*context));
     context->cmdlist = commands;
     context->interface = interface;
@@ -269,14 +276,23 @@
     context->buffer.data = input_buffer;
     context->buffer.length = input_buffer_length;
     context->buffer.position = 0;
-    context->error_info_heap.data = error_info_heap;
-    context->error_info_heap.wr = 0;
-    context->error_info_heap.size = error_info_heap_length;
-    context->error_info_heap.count = context->error_info_heap.size;
-    memset(context->error_info_heap.data, 0, context->error_info_heap.size);
     SCPI_ErrorInit(context, error_queue_data, error_queue_size);
 }
 
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
+/**
+ * Initialize context's
+ * @param context
+ * @param data
+ * @param len
+ * @return
+ */
+void SCPI_InitHeap(scpi_t * context,
+        char * error_info_heap, size_t error_info_heap_length) {
+    scpiheap_init(&context->error_info_heap, error_info_heap, error_info_heap_length);
+}
+#endif
+
 /**
  * Interface to the application. Adds data to system buffer and try to search
  * command line termination. If the termination is found or if len=0, command
diff --git a/libscpi/src/utils.c b/libscpi/src/utils.c
index ae2c2c6..cb34cc7 100644
--- a/libscpi/src/utils.c
+++ b/libscpi/src/utils.c
@@ -753,6 +753,21 @@
 #if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
 
 /**
+ * Initialize heap structure
+ * @param heap - pointer to manual allocated heap buffer
+ * @param error_info_heap - buffer for the heap
+ * @param error_info_heap_length - length of the heap
+ */
+void scpiheap_init(scpi_error_info_heap_t * heap, char * error_info_heap, size_t error_info_heap_length)
+{
+    heap->data = error_info_heap;
+    heap->wr = 0;
+    heap->size = error_info_heap_length;
+    heap->count = heap->size;
+    memset(heap->data, 0, heap->size);
+}
+
+/**
  * Duplicate string if "strdup" ("malloc/free") not supported on system.
  * Allocate space in heap if it possible
  *
@@ -760,8 +775,8 @@
  * @param s - current pointer of duplication string
  * @return - pointer of duplicated string or NULL, if duplicate is not possible.
  */
-char * OUR_strndup(scpi_error_info_heap_t * heap, const char *s, size_t n) {
-    if (!s || !heap) {
+char * scpiheap_strndup(scpi_error_info_heap_t * heap, const char *s, size_t n) {
+    if (!s || !heap || !heap->size) {
         return NULL;
     }
 
@@ -793,6 +808,12 @@
     heap->wr += len;
     heap->count -= len;
 
+    // ensure '\0' a the end
+    if (heap->wr > 0) {
+        heap->data[heap->wr - 1] = '\0';
+    } else {
+        heap->data[heap->size - 1] = '\0';
+    }
     return head;
 }
 
@@ -805,7 +826,7 @@
  * @return s2 - pointer of second part of string, if string splited .
  * @return len2 - lenght of second part of string.
  */
-scpi_bool_t OUR_get_parts(scpi_error_info_heap_t * heap, const char * s, size_t * len1, const char ** s2, size_t * len2) {
+scpi_bool_t scpiheap_get_parts(scpi_error_info_heap_t * heap, const char * s, size_t * len1, const char ** s2, size_t * len2) {
     if (!heap || !s || !len1 || !s2 || !len2) {
         return FALSE;
     }
@@ -835,14 +856,14 @@
  * @param s - pointer of duplicate string
  * @param rollback - backward write pointer in heap
  */
-void OUR_free(scpi_error_info_heap_t * heap, char * s, scpi_bool_t rollback) {
+void scpiheap_free(scpi_error_info_heap_t * heap, char * s, scpi_bool_t rollback) {
 
     if (!s) return;
 
     char * data_add;
     size_t len[2];
 
-    if (!OUR_get_parts(heap, s, &len[0], (const char **)&data_add, &len[1])) return;
+    if (!scpiheap_get_parts(heap, s, &len[0], (const char **)&data_add, &len[1])) return;
 
     if (data_add) {
         len[1]++;
diff --git a/libscpi/src/utils_private.h b/libscpi/src/utils_private.h
index 9252dcc..ba1f8fc 100644
--- a/libscpi/src/utils_private.h
+++ b/libscpi/src/utils_private.h
@@ -88,9 +88,10 @@
 #endif
 
 #if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
-	char * OUR_strndup(scpi_error_info_heap_t * heap, const char *s, size_t n) LOCAL;
-	void OUR_free(scpi_error_info_heap_t * heap, char *s, scpi_bool_t rollback) LOCAL;
-	scpi_bool_t OUR_get_parts(scpi_error_info_heap_t * heap, const char *s1, size_t * len1, const char ** s2, size_t * len2) LOCAL;
+    void scpiheap_init(scpi_error_info_heap_t * heap, char * error_info_heap, size_t error_info_heap_length);
+    char * scpiheap_strndup(scpi_error_info_heap_t * heap, const char *s, size_t n) LOCAL;
+    void scpiheap_free(scpi_error_info_heap_t * heap, char *s, scpi_bool_t rollback) LOCAL;
+    scpi_bool_t scpiheap_get_parts(scpi_error_info_heap_t * heap, const char *s1, size_t * len1, const char ** s2, size_t * len2) LOCAL;
 #endif
 
 #ifndef min
diff --git a/libscpi/test/test_parser.c b/libscpi/test/test_parser.c
index bc11f74..5d64527 100644
--- a/libscpi/test/test_parser.c
+++ b/libscpi/test/test_parser.c
@@ -186,6 +186,9 @@
 #define SCPI_ERROR_QUEUE_SIZE 4
 static scpi_error_t scpi_error_queue_data[SCPI_ERROR_QUEUE_SIZE];
 
+#define SCPI_ERROR_INFO_HEAP_SIZE 100
+static char error_info_heap[SCPI_ERROR_INFO_HEAP_SIZE];
+
 static int init_suite(void) {
     SCPI_Init(&scpi_context,
             scpi_commands,
@@ -193,8 +196,11 @@
             scpi_units_def,
             "MA", "IN", NULL, "VER",
             scpi_input_buffer, SCPI_INPUT_BUFFER_LENGTH,
-            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE,
-            NULL, 0);
+            scpi_error_queue_data, SCPI_ERROR_QUEUE_SIZE);
+#if USE_DEVICE_DEPENDENT_ERROR_INFORMATION && !USE_MEMORY_ALLOCATION_FREE
+    SCPI_InitHeap(&scpi_context,
+            error_info_heap, SCPI_ERROR_INFO_HEAP_SIZE);
+#endif
 
     return 0;
 }

--
Gitblit v1.9.1