EPICS Controls Argonne National Laboratory

Experimental Physics and
Industrial Control System

2002  2003  2004  2005  2006  2007  2008  2009  <20102011  2012  2013  2014  2015  2016  2017  2018  2019  2020  2021  2022  2023  2024  Index 2002  2003  2004  2005  2006  2007  2008  2009  <20102011  2012  2013  2014  2015  2016  2017  2018  2019  2020  2021  2022  2023  2024 
<== Date ==> <== Thread ==>

Subject: [PATCH 3/4] Add autosizing array support for caget and camonitor.
From: Michael Abbott <[email protected]>
To: undisclosed-recipients:;
Date: Wed, 2 Jun 2010 13:51:08 +0100
Signed-off-by: Michael Abbott <[email protected]>
---
 src/catools/caget.c     |   30 ++++++++++++++++--------------
 src/catools/camonitor.c |   11 +++++------
 src/catools/tool_lib.c  |    6 +++---
 src/catools/tool_lib.h  |    4 ++--
 4 files changed, 26 insertions(+), 25 deletions(-)

diff --git a/src/catools/caget.c b/src/catools/caget.c
index bae87e7..573ae85 100644
--- a/src/catools/caget.c
+++ b/src/catools/caget.c
@@ -127,6 +127,7 @@ static void event_handler (evargs args)
         ppv->value   = calloc(1, dbr_size_n(args.type, args.count));
         memcpy(ppv->value, args.dbr, dbr_size_n(args.type, args.count));
         ppv->onceConnected = 1;
+        ppv->nElems = args.count;
         nRead++;
     }
 }
@@ -183,11 +184,9 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
             }
         }
                                 /* Adjust array count */
-        if (reqElems == 0 || pvs[n].nElems < reqElems){
-            pvs[n].reqElems = pvs[n].nElems; /* Use full number of points */
-        } else {
-            pvs[n].reqElems = reqElems;      /* Limit to specified number */
-        }
+        if (reqElems > pvs[n].nElems)
+            reqElems = pvs[n].nElems;
+        pvs[n].reqElems = reqElems;
 
                                 /* Issue CA request */
                                 /* ---------------- */
@@ -205,13 +204,13 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                                                (void*)&pvs[n]);
             } else {
                                        /* Allocate value structure */
-                pvs[n].value = calloc(1, dbr_size_n(pvs[n].dbrType, pvs[n].reqElems));
+                pvs[n].value = calloc(1, dbr_size_n(pvs[n].dbrType, pvs[n].nElems));
                 if(!pvs[n].value) {
                     fprintf(stderr,"Allocation failed\n");
                     return 1;
                 }
                 result = ca_array_get(pvs[n].dbrType,
-                                      pvs[n].reqElems,
+                                      pvs[n].nElems,
                                       pvs[n].chid,
                                       pvs[n].value);
             }
@@ -253,10 +252,13 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                                 /* -------------- */
 
     for (n = 0; n < nPvs; n++) {
+        /* Truncate the data printed to what was requested. */
+        if (pvs[n].reqElems != 0  && pvs[n].nElems > pvs[n].reqElems)
+            pvs[n].nElems = pvs[n].reqElems;
 
         switch (format) {
         case plain:             /* Emulate old caget behaviour */
-            if (pvs[n].reqElems <= 1 && fieldSeparator == ' ') printf("%-30s", pvs[n].name);
+            if (pvs[n].nElems <= 1 && fieldSeparator == ' ') printf("%-30s", pvs[n].name);
             else                                               printf("%s", pvs[n].name);
             printf("%c", fieldSeparator);
         case terse:
@@ -270,7 +272,7 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                 printf("*** no data available (timeout)\n");
             else
             {
-                if (charArrAsStr && dbr_type_is_CHAR(pvs[n].dbrType) && (reqElems || pvs[n].reqElems > 1)) {
+                if (charArrAsStr && dbr_type_is_CHAR(pvs[n].dbrType) && (reqElems || pvs[n].nElems > 1)) {
                     dbr_char_t *s = (dbr_char_t*) dbr_value_ptr(pvs[n].value, pvs[n].dbrType);
                     int dlen = epicsStrnEscapedFromRawSize((char*)s, strlen((char*)s));
                     char *d = calloc(dlen+1, sizeof(char));
@@ -282,8 +284,8 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                         fprintf(stderr,"Failed to allocate space for escaped string\n");
                     }
                 } else {
-                    if (reqElems || pvs[n].nElems > 1) printf("%lu%c", pvs[n].reqElems, fieldSeparator);
-                    for (i=0; i<pvs[n].reqElems; ++i) {
+                    if (reqElems || pvs[n].nElems > 1) printf("%lu%c", pvs[n].nElems, fieldSeparator);
+                    for (i=0; i<pvs[n].nElems; ++i) {
                         if (i) printf ("%c", fieldSeparator);
                         printf("%s", val2str(pvs[n].value, pvs[n].dbrType, i));
                     }
@@ -315,8 +317,8 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                 else {
                     printf("    Element count:    %lu\n"
                            "    Value:            ",
-                           pvs[n].reqElems);
-                    if (charArrAsStr && dbr_type_is_CHAR(pvs[n].dbrType) && (reqElems || pvs[n].reqElems > 1)) {
+                           pvs[n].nElems);
+                    if (charArrAsStr && dbr_type_is_CHAR(pvs[n].dbrType) && (reqElems || pvs[n].nElems > 1)) {
                         dbr_char_t *s = (dbr_char_t*) dbr_value_ptr(pvs[n].value, pvs[n].dbrType);
                         int dlen = epicsStrnEscapedFromRawSize((char*)s, strlen((char*)s));
                         char *d = calloc(dlen+1, sizeof(char));
@@ -328,7 +330,7 @@ static int caget (pv *pvs, int nPvs, RequestT request, OutputT format,
                             fprintf(stderr,"Failed to allocate space for escaped string\n");
                         }
                     } else {
-                        for (i=0; i<pvs[n].reqElems; ++i) {
+                        for (i=0; i<pvs[n].nElems; ++i) {
                             if (i) printf ("%c", fieldSeparator);
                             printf("%s", val2str(pvs[n].value, pvs[n].dbrType, i));
                         }
diff --git a/src/catools/camonitor.c b/src/catools/camonitor.c
index 82ee20f..8e6b14e 100644
--- a/src/catools/camonitor.c
+++ b/src/catools/camonitor.c
@@ -107,6 +107,7 @@ static void event_handler (evargs args)
     if (args.status == ECA_NORMAL)
     {
         pv->dbrType = args.type;
+        pv->nElems = args.count;
         memcpy(pv->value, args.dbr, dbr_size_n(args.type, args.count));
 
         print_time_val_sts(pv, reqElems);
@@ -150,11 +151,9 @@ static void connection_handler ( struct connection_handler_args args )
             ppv->dbrType = DBR_TIME_STRING;
         }
                                 /* Adjust array count */
-        if (reqElems == 0 || ppv->nElems < reqElems){
-            ppv->reqElems = ppv->nElems; /* Use full number of points */
-        } else {
-            ppv->reqElems = reqElems; /* Limit to specified number */
-        }
+        if (reqElems > ppv->nElems)
+            reqElems = ppv->nElems;
+        ppv->reqElems = reqElems;
 
         ppv->onceConnected = 1;
         nConn++;
@@ -163,7 +162,7 @@ static void connection_handler ( struct connection_handler_args args )
         /* install monitor once with first connect */
         if ( ! ppv->value ) {
                                     /* Allocate value structure */
-            ppv->value = calloc(1, dbr_size_n(ppv->dbrType, ppv->reqElems));
+            ppv->value = calloc(1, dbr_size_n(ppv->dbrType, ppv->nElems));
             if ( ppv->value ) {
                 ppv->status = ca_create_subscription(ppv->dbrType,
                                                 ppv->reqElems,
diff --git a/src/catools/tool_lib.c b/src/catools/tool_lib.c
index 0bfcab3..13d6330 100644
--- a/src/catools/tool_lib.c
+++ b/src/catools/tool_lib.c
@@ -455,8 +455,8 @@ char *dbr2str (const void *value, unsigned type)
             printf("Failed to allocate for print_time_val_sts\n");      \
         }                                                               \
     } else {                                                            \
-        if (reqElems || pv->nElems > 1) printf("%c%lu", fieldSeparator, pv->reqElems); \
-        for (i=0; i<pv->reqElems; ++i) {                                \
+        if (reqElems || pv->nElems > 1) printf("%c%lu", fieldSeparator, pv->nElems); \
+        for (i=0; i<pv->nElems; ++i) {                                \
             printf("%c%s", fieldSeparator, val2str(value, TYPE_ENUM, i)); \
         }                                                               \
     }                                                                   \
@@ -492,7 +492,7 @@ void print_time_val_sts (pv* pv, unsigned long reqElems)
         tsInitS = 1;
     }
 
-    if (pv->reqElems <= 1 && fieldSeparator == ' ') printf("%-30s", pv->name);
+    if (pv->nElems <= 1 && fieldSeparator == ' ') printf("%-30s", pv->name);
     else                                            printf("%s", pv->name);
     printf("%c", fieldSeparator);
     if (!pv->onceConnected)
diff --git a/src/catools/tool_lib.h b/src/catools/tool_lib.h
index 5bb6b5d..baebf79 100644
--- a/src/catools/tool_lib.h
+++ b/src/catools/tool_lib.h
@@ -64,8 +64,8 @@ typedef struct
     chid  chid;
     long  dbfType;
     long  dbrType;
-    unsigned long nElems;
-    unsigned long reqElems;
+    unsigned long nElems;       // True length of data in value
+    unsigned long reqElems;     // Requested length of data
     int status;
     void* value;
     epicsTimeStamp tsPreviousC;
-- 
1.6.6.1


References:
[PATCH 0/4] Adding dynamic arrays to EPICS Channel Access Michael Abbott

Navigate by Date:
Prev: EPICS protocol header Michael Abbott
Next: [PATCH 0/4] Adding dynamic arrays to EPICS Channel Access Michael Abbott
Index: 2002  2003  2004  2005  2006  2007  2008  2009  <20102011  2012  2013  2014  2015  2016  2017  2018  2019  2020  2021  2022  2023  2024 
Navigate by Thread:
Prev: [PATCH 4/4] Drive-by refactoring in caserverio.c Michael Abbott
Next: [Merge] lp:~michael-abbott/epics-base/dynamic-array into lp:epics-base Michael Abbott
Index: 2002  2003  2004  2005  2006  2007  2008  2009  <20102011  2012  2013  2014  2015  2016  2017  2018  2019  2020  2021  2022  2023  2024 
ANJ, 02 Feb 2012 Valid HTML 4.01! · Home · News · About · Base · Modules · Extensions · Distributions · Download ·
· Search · EPICS V4 · IRMIS · Talk · Bugs · Documents · Links · Licensing ·