LAL  7.5.0.1-b72065a
UserInputPrint.c
Go to the documentation of this file.
1 //
2 // Copyright (C) 2016 Karl Wette
3 // Copyright (C) 2015 Reinhard Prix
4 //
5 // This program is free software; you can redistribute it and/or modify
6 // it under the terms of the GNU General Public License as published by
7 // the Free Software Foundation; either version 2 of the License, or
8 // (at your option) any later version.
9 //
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
14 //
15 // You should have received a copy of the GNU General Public License
16 // along with with program; see the file COPYING. If not, write to the
17 // Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
18 // MA 02110-1301 USA
19 //
20 
21 #include <stdio.h>
22 #include <string.h>
23 
24 #include <lal/LALMalloc.h>
25 #include <lal/LALStdio.h>
26 #include <lal/LALString.h>
27 #include <lal/XLALError.h>
28 #include <lal/Date.h>
29 #include <lal/LALDatatypes.h>
30 
31 #include <lal/UserInputPrint.h>
32 
33 // ==================== function definitions ====================
34 
35 /// Return 'string value' (allocated here) of an INT8
36 char *
37 XLALPrintStringValueOfINT8 ( const INT8 *valINT8 )
38 {
39  XLAL_CHECK_NULL ( valINT8 != NULL, XLAL_EINVAL );
40  char buf[256];
41  sprintf ( buf, "%" LAL_INT8_FORMAT, (*valINT8) );
42  return XLALStringDuplicate ( buf );
43 }
44 
45 /// Return 'string value' (allocated here) of an INT4
46 char *
47 XLALPrintStringValueOfINT4 ( const INT4 *valINT4 )
48 {
49  XLAL_CHECK_NULL ( valINT4 != NULL, XLAL_EINVAL );
50  char buf[256];
51  sprintf ( buf, "%" LAL_INT4_FORMAT, (*valINT4) );
52  return XLALStringDuplicate ( buf );
53 }
54 
55 /// Return 'string value' (allocated here) of an UINT8
56 char *
58 {
59  XLAL_CHECK_NULL ( valUINT8 != NULL, XLAL_EINVAL );
60  char buf[256];
61  sprintf ( buf, "%" LAL_UINT8_FORMAT, (*valUINT8) );
62  return XLALStringDuplicate ( buf );
63 }
64 
65 /// Return 'string value' (allocated here) of an UINT4
66 char *
68 {
69  XLAL_CHECK_NULL ( valUINT4 != NULL, XLAL_EINVAL );
70  char buf[256];
71  sprintf ( buf, "%" LAL_UINT4_FORMAT, (*valUINT4) );
72  return XLALStringDuplicate ( buf );
73 }
74 
75 /// Return 'string value' (allocated here) of a REAL8 (printed at full precision)
76 char *
78 {
79  XLAL_CHECK_NULL ( valREAL8 != NULL, XLAL_EINVAL );
80  char buf[256];
81  sprintf ( buf, "%.16" LAL_REAL8_FORMAT, (*valREAL8) );
82  return XLALStringDuplicate ( buf );
83 }
84 
85 /// Return 'string value' (allocated here) of a REAL4 (printed at full precision)
86 char *
88 {
89  XLAL_CHECK_NULL ( valREAL4 != NULL, XLAL_EINVAL );
90  char buf[256];
91  sprintf ( buf, "%.8" LAL_REAL4_FORMAT, (*valREAL4) );
92  return XLALStringDuplicate ( buf );
93 }
94 
95 /// Return 'string value' (allocated here) of a BOOLEAN
96 char *
98 {
99  XLAL_CHECK_NULL ( valBOOLEAN != NULL, XLAL_EINVAL );
100  char buf[256];
101  sprintf ( buf, (*valBOOLEAN) ? "TRUE" : "FALSE" );
102  return XLALStringDuplicate ( buf );
103 }
104 
105 
106 /// Return 'string value' (allocated here) of a GPS epoch, as parseable by XLALParseStringValueAs[GPS|EPOCH]()
107 char *
109 {
110  XLAL_CHECK_NULL ( valGPS != NULL, XLAL_EINVAL );
111  char buf[256];
112  XLAL_CHECK_NULL ( XLALGPSToStr ( buf, valGPS ) != NULL, XLAL_EFUNC );
113  return XLALStringDuplicate ( buf );
114 }
115 
116 /// Return 'string value' (allocated here) of a STRING, surrounded by double quotes.
117 /// The output is parseable by XLALParseStringValueAsSTRING().
118 /// In case of NULL input, returns the string 'NULL'.
119 char *
121 {
122  XLAL_CHECK_NULL ( valSTRING != NULL, XLAL_EINVAL );
123 
124  char *ret;
125  if ( (*valSTRING) == NULL )
126  {
127  XLAL_CHECK_NULL ( (ret = XLALStringDuplicate("NULL")) != NULL, XLAL_EFUNC );
128  }
129  else
130  {
131  XLAL_CHECK_NULL ( (ret = XLALMalloc ( strlen((*valSTRING)) + 2 + 1)) != NULL, XLAL_ENOMEM ); // +surrounding quotes + terminating-0
132  sprintf ( ret, "\"%s\"", (*valSTRING) );
133  }
134 
135  return ret;
136 
137 } // XLALPrintStringValueOfSTRING()
138 
139 /// Return 'string value' (allocated here) of a INT4Range, as parseable by XLALParseStringValueAsINT4Range()
140 char *
142  XLAL_CHECK_NULL(int4Range != NULL, XLAL_EFAULT);
143  char *part0 = XLALPrintStringValueOfINT4(&(*int4Range)[0]);
144  XLAL_CHECK_NULL(part0 != NULL, XLAL_EFUNC);
145  char *part1 = XLALPrintStringValueOfINT4(&(*int4Range)[1]);
146  XLAL_CHECK_NULL(part1 != NULL, XLAL_EFUNC);
147  char *retn = XLALMalloc(sizeof(*retn) * (strlen(part0) + 1 + strlen(part1) + 1));
148  XLAL_CHECK_NULL(retn != NULL, XLAL_ENOMEM);
149  strcpy(retn, part0);
150  strcat(retn, ",");
151  strcat(retn, part1);
152  XLALFree(part0);
153  XLALFree(part1);
154  return retn;
155 }
156 
157 
158 /// Return 'string value' (allocated here) of a REAL8Range, as parseable by XLALParseStringValueAsREAL8Range()
159 char *
161  XLAL_CHECK_NULL(real8Range != NULL, XLAL_EFAULT);
162  char *part0 = XLALPrintStringValueOfREAL8(&(*real8Range)[0]);
163  XLAL_CHECK_NULL(part0 != NULL, XLAL_EFUNC);
164  char *part1 = XLALPrintStringValueOfREAL8(&(*real8Range)[1]);
165  XLAL_CHECK_NULL(part1 != NULL, XLAL_EFUNC);
166  char *retn = XLALMalloc(sizeof(*retn) * (strlen(part0) + 1 + strlen(part1) + 1));
167  XLAL_CHECK_NULL(retn != NULL, XLAL_ENOMEM);
168  strcpy(retn, part0);
169  strcat(retn, ",");
170  strcat(retn, part1);
171  XLALFree(part0);
172  XLALFree(part1);
173  return retn;
174 }
175 
176 
177 /// Return 'string value' (allocated here) of a EPOCHRange, as parseable by XLALParseStringValueAsEPOCHRange()
178 char *
180  XLAL_CHECK_NULL(gpsRange != NULL, XLAL_EFAULT);
181  char *part0 = XLALPrintStringValueOfEPOCH(&(*gpsRange)[0]);
182  XLAL_CHECK_NULL(part0 != NULL, XLAL_EFUNC);
183  char *part1 = XLALPrintStringValueOfEPOCH(&(*gpsRange)[1]);
184  XLAL_CHECK_NULL(part1 != NULL, XLAL_EFUNC);
185  char *retn = XLALMalloc(sizeof(*retn) * (strlen(part0) + 1 + strlen(part1) + 1));
186  XLAL_CHECK_NULL(retn != NULL, XLAL_ENOMEM);
187  strcpy(retn, part0);
188  strcat(retn, ",");
189  strcat(retn, part1);
190  XLALFree(part0);
191  XLALFree(part1);
192  return retn;
193 }
194 
195 
196 /// Return 'string value' (allocated here) of a user selection of an enumeration value.
197 /// The output is parseable by XLALParseStringValueOfUserEnum().
198 char*
199 XLALPrintStringValueOfUserEnum ( const int *valEnum, const UserChoices *enumData )
200 {
201 
202  // Check input
203  XLAL_CHECK_NULL(valEnum != NULL, XLAL_EFAULT);
204  XLAL_CHECK_NULL(*valEnum >= 0, XLAL_EINVAL);
205  XLAL_CHECK_NULL(enumData != NULL, XLAL_EFAULT);
206 
207  // Select name of enumeration value
208  for ( size_t i = 0; i < XLAL_NUM_ELEM(*enumData); ++i ) {
209  if ((*enumData)[i].val >= 0 && (*enumData)[i].name != NULL) {
210  if (*valEnum == (*enumData)[i].val) {
211  return XLALStringDuplicate((*enumData)[i].name);
212  }
213  }
214  }
215 
216  XLAL_ERROR_NULL( XLAL_EINVAL, "Value '%i' is not a valid enumeration value", *valEnum );
217 
218 }
219 
220 
221 /// Return format help string (allocated here) for a user selection of an enumeration value.
222 char*
224 {
225 
226  // Check input
227  XLAL_CHECK_NULL(enumData != NULL, XLAL_EFAULT);
228 
229  // Generate format help string
230  CHAR *str = NULL;
231  int prev_val = -1;
232  const char *prev_name = NULL;
233  for ( size_t i = 0; i < XLAL_NUM_ELEM(*enumData); ++i ) {
234  if ((*enumData)[i].val >= 0 && (*enumData)[i].name != NULL) {
235  if (prev_name != NULL && strcmp(prev_name, (*enumData)[i].name) == 0) {
236  continue;
237  }
238  if (str == NULL) {
239  str = XLALStringAppendFmt( str, "=(%s", (*enumData)[i].name);
240  } else if (prev_val >= 0 && prev_val == (*enumData)[i].val) {
241  str = XLALStringAppendFmt( str, "=%s", (*enumData)[i].name);
242  } else {
243  str = XLALStringAppendFmt( str, "|%s", (*enumData)[i].name);
244  }
245  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
246  prev_val = (*enumData)[i].val;
247  prev_name = (*enumData)[i].name;
248  }
249  }
250  str = XLALStringAppendFmt( str, ")");
251  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
252 
253  return str;
254 
255 }
256 
257 
258 /// Return 'string value' (allocated here) of a user selection of an bitflag value.
259 /// The output is parseable by XLALParseStringValueOfUserFlag().
260 char*
261 XLALPrintStringValueOfUserFlag ( const int *valFlag, const UserChoices *flagData )
262 {
263 
264  // Check input
265  XLAL_CHECK_NULL(valFlag != NULL, XLAL_EFAULT);
266  XLAL_CHECK_NULL(*valFlag >= 0, XLAL_EINVAL);
267  XLAL_CHECK_NULL(flagData != NULL, XLAL_EFAULT);
268 
269  // Handle special case of first bitflag with value 0, representing a zero bitflag
270  if ((*flagData)[0].val == 0 && (*flagData)[0].name != NULL && *valFlag == 0) {
271  return XLALStringDuplicate( (*flagData)[0].name );
272  }
273 
274  // Deduce bitflag value
275  int val = *valFlag;
276  CHAR *str = NULL;
277  for ( size_t i = 0; i < XLAL_NUM_ELEM(*flagData); ++i ) {
278  if ((*flagData)[i].val > 0 && (*flagData)[i].name != NULL) {
279  if (val & (*flagData)[i].val) {
280  val &= ~(*flagData)[i].val;
281  str = XLALStringAppendFmt( str, "%s%s", ( str == NULL ? "" : "," ), (*flagData)[i].name);
282  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
283  }
284  }
285  }
286  XLAL_CHECK_NULL( val == 0, XLAL_EINVAL, "Value '%i' is not a valid bitflag value", *valFlag );
287 
288  return str;
289 
290 }
291 
292 
293 /// Return format help string (allocated here) for a user selection of an bitflag value.
294 char*
296 {
297 
298  // Check input
299  XLAL_CHECK_NULL(flagData != NULL, XLAL_EFAULT);
300 
301  // Generate format help string
302  CHAR *str = NULL;
303  int prev_val = 0;
304  const char *prev_name = NULL;
305  for ( size_t i = 0; i < XLAL_NUM_ELEM(*flagData); ++i ) {
306  if ((*flagData)[i].val > 0 && (*flagData)[i].name != NULL) {
307  if (prev_name != NULL && strcmp(prev_name, (*flagData)[i].name) == 0) {
308  continue;
309  }
310  if (str == NULL) {
311  str = XLALStringAppendFmt( str, "=(%s", (*flagData)[i].name);
312  } else if (prev_val > 0 && prev_val == (*flagData)[i].val ) {
313  str = XLALStringAppendFmt( str, "=%s", (*flagData)[i].name);
314  } else {
315  str = XLALStringAppendFmt( str, "|%s", (*flagData)[i].name);
316  }
317  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
318  prev_val = (*flagData)[i].val;
319  prev_name = (*flagData)[i].name;
320  }
321  }
322  str = XLALStringAppendFmt( str, ")[,...]");
323  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
324  if ((*flagData)[0].val == 0 && (*flagData)[0].name != NULL) {
325  CHAR *old_str = str;
326  str = XLALStringAppendFmt( NULL, "=%s|(%s)", (*flagData)[0].name, old_str + 1);
327  XLAL_CHECK_NULL(str != NULL, XLAL_EFUNC);
328  XLALFree(old_str);
329  }
330 
331  return str;
332 
333 }
334 
335 
336 /// Return 'string value' (allocated here) of a STRINGVector, by turning into comma-separated list of strings, each surrounded by single quotes.
337 /// The output is parseable by XLALParseStringValueAsSTRINGVector().
338 /// In case of a NULL or empty vector (data==NULL|length==0), generate the string 'NULL'.
339 char *
341 {
342  XLAL_CHECK_NULL ( valSTRINGVector != NULL, XLAL_EINVAL );
343  char *ret = NULL;
344  if ( (*valSTRINGVector == NULL) || ((*valSTRINGVector)->data == NULL) || ((*valSTRINGVector)->length == 0) )
345  {
346  XLAL_CHECK_NULL ( (ret = XLALStringDuplicate("NULL")) != NULL, XLAL_EFUNC );
347  }
348  else
349  {
350  for ( UINT4 i=0; i < (*valSTRINGVector)->length; i++ )
351  {
352  if ( i != 0 ) {
353  XLAL_CHECK_NULL ( (ret = XLALStringAppend ( ret, "," )) != NULL, XLAL_EFUNC );
354  }
355  char *stringi;
356  XLAL_CHECK_NULL ( (stringi = XLALPrintStringValueOfSTRING ( &((*valSTRINGVector)->data[i]) )) != NULL, XLAL_EFUNC );
357  XLAL_CHECK_NULL ( (ret = XLALStringAppend ( ret, stringi )) != NULL, XLAL_EFUNC );
358  XLALFree ( stringi );
359  } // for i < length
360  } // end: if valSTRING != NULL
361 
362  return ret;
363 
364 } // XLALPrintStringValueOfSTRINGVector()
365 
366 ///
367 /// Return 'string value' (allocated here) of a <CTYPE>Vector, by turning into comma-separated list of <CTYPE> values.
368 /// The output is parseable by XLALParseStringValueAs<CTYPE>Vector().
369 /// In case of a NULL or empty vector (data==NULL|length==0), generate the string 'NULL'.
370 #define DEFN_XLALPrintStringValueOfVector(CTYPE) \
371 DECL_XLALPrintStringValueOfVector(CTYPE) \
372 { \
373  XLAL_CHECK_NULL ( valVector != NULL, XLAL_EINVAL ); \
374  char *ret = NULL; \
375  if ( (*valVector == NULL) || ((*valVector)->data == NULL) || ((*valVector)->length == 0) ) \
376  { \
377  XLAL_CHECK_NULL ( (ret = XLALStringDuplicate("NULL")) != NULL, XLAL_EFUNC ); \
378  } \
379  else \
380  { \
381  for ( UINT4 i=0; i < (*valVector)->length; i++ ) \
382  { \
383  if ( i != 0 ) { \
384  XLAL_CHECK_NULL ( (ret = XLALStringAppend ( ret, "," )) != NULL, XLAL_EFUNC ); \
385  } \
386  char *tmp; \
387  XLAL_CHECK_NULL ( (tmp = XLALPrintStringValueOf##CTYPE ( &(*valVector)->data[i])) != NULL, XLAL_EFUNC ); \
388  XLAL_CHECK_NULL ( (ret = XLALStringAppend ( ret, tmp )) != NULL, XLAL_EFUNC ); \
389  XLALFree ( tmp ); \
390  } /* for i < length */ \
391  } /* end: if non-empty input vector */ \
392  \
393  return ret; \
394  \
395 } /* XLALPrintStringValueOf<CYPTE>Vector() */
396 
char * XLALStringAppendFmt(char *s, const char *fmt,...)
Append the formatted string 'fmt' to the string 's', which is reallocated with XLALRealloc() to the r...
Definition: LALString.c:69
const char *const name
type name
Definition: UserInput.c:193
#define DEFN_XLALPrintStringValueOfVector(CTYPE)
Return 'string value' (allocated here) of a <CTYPE>Vector, by turning into comma-separated list of <C...
char * XLALGPSToStr(char *, const LIGOTimeGPS *t)
Return a string containing the ASCII base 10 representation of a LIGOTimeGPS.
Definition: StrToGPS.c:274
unsigned char BOOLEAN
Boolean logical type, see Headers LAL(Atomic)Datatypes.h for more details.
#define XLAL_NUM_ELEM(x)
MACRO which gives the number of elements in a fixed-size array.
uint64_t UINT8
Eight-byte unsigned integer; on some platforms this is equivalent to unsigned long int instead.
double REAL8
Double precision real floating-point number (8 bytes).
int64_t INT8
Eight-byte signed integer; on some platforms this is equivalent to long int instead.
char CHAR
One-byte signed integer, see Headers LAL(Atomic)Datatypes.h for more details.
uint32_t UINT4
Four-byte unsigned integer.
int32_t INT4
Four-byte signed integer.
float REAL4
Single precision real floating-point number (4 bytes).
#define XLALMalloc(n)
Definition: LALMalloc.h:44
#define XLALFree(p)
Definition: LALMalloc.h:47
#define LAL_REAL8_FORMAT
Definition: LALStdio.h:133
#define LAL_INT8_FORMAT
Definition: LALStdio.h:128
#define LAL_INT4_FORMAT
Definition: LALStdio.h:127
#define LAL_REAL4_FORMAT
Definition: LALStdio.h:132
#define LAL_UINT8_FORMAT
Definition: LALStdio.h:131
#define LAL_UINT4_FORMAT
Definition: LALStdio.h:130
char * XLALStringDuplicate(const char *s)
Like strdup but uses LAL allocation routines (free with LALFree).
Definition: LALString.c:89
char * XLALStringAppend(char *s, const char *append)
Like strcat but dynamically reallocates string with LALRealloc.
Definition: LALString.c:50
LIGOTimeGPS LIGOTimeGPSRange[2]
A range of GPS times; first element is minimum, second element is maximum of range.
REAL8 REAL8Range[2]
A range of REAL8 values; first element is minimum, second element is maximum of range.
INT4 INT4Range[2]
A range of INT4 values; first element is minimum, second element is maximum of range.
char * XLALPrintStringValueOfREAL8Range(const REAL8Range *real8Range)
Return 'string value' (allocated here) of a REAL8Range, as parseable by XLALParseStringValueAsREAL8Ra...
char * XLALFormatHelpStringOfUserEnum(const UserChoices *enumData)
Return format help string (allocated here) for a user selection of an enumeration value.
char * XLALPrintStringValueOfINT4Range(const INT4Range *int4Range)
Return 'string value' (allocated here) of a INT4Range, as parseable by XLALParseStringValueAsINT4Rang...
char * XLALPrintStringValueOfSTRING(CHAR **valSTRING)
Return 'string value' (allocated here) of a STRING, surrounded by double quotes.
char * XLALPrintStringValueOfUserFlag(const int *valFlag, const UserChoices *flagData)
Return 'string value' (allocated here) of a user selection of an bitflag value.
char * XLALPrintStringValueOfSTRINGVector(LALStringVector **valSTRINGVector)
Return 'string value' (allocated here) of a STRINGVector, by turning into comma-separated list of str...
char * XLALPrintStringValueOfINT4(const INT4 *valINT4)
Return 'string value' (allocated here) of an INT4.
char * XLALPrintStringValueOfEPOCH(const LIGOTimeGPS *valGPS)
Return 'string value' (allocated here) of a GPS epoch, as parseable by XLALParseStringValueAs[GPS|EPO...
char * XLALPrintStringValueOfINT8(const INT8 *valINT8)
Return 'string value' (allocated here) of an INT8.
char * XLALPrintStringValueOfUINT8(const UINT8 *valUINT8)
Return 'string value' (allocated here) of an UINT8.
char * XLALPrintStringValueOfUINT4(const UINT4 *valUINT4)
Return 'string value' (allocated here) of an UINT4.
char * XLALPrintStringValueOfUserEnum(const int *valEnum, const UserChoices *enumData)
Return 'string value' (allocated here) of a user selection of an enumeration value.
char * XLALPrintStringValueOfREAL4(const REAL4 *valREAL4)
Return 'string value' (allocated here) of a REAL4 (printed at full precision)
char * XLALPrintStringValueOfREAL8(const REAL8 *valREAL8)
Return 'string value' (allocated here) of a REAL8 (printed at full precision)
char * XLALPrintStringValueOfEPOCHRange(const LIGOTimeGPSRange *gpsRange)
Return 'string value' (allocated here) of a EPOCHRange, as parseable by XLALParseStringValueAsEPOCHRa...
char * XLALFormatHelpStringOfUserFlag(const UserChoices *flagData)
Return format help string (allocated here) for a user selection of an bitflag value.
char * XLALPrintStringValueOfBOOLEAN(const BOOLEAN *valBOOLEAN)
Return 'string value' (allocated here) of a BOOLEAN.
#define XLAL_ERROR_NULL(...)
Macro to invoke a failure from a XLAL routine returning a pointer.
Definition: XLALError.h:713
#define XLAL_CHECK_NULL(assertion,...)
Macro to test an assertion and invoke a failure if it is not true in a function that returns a pointe...
Definition: XLALError.h:825
@ XLAL_ENOMEM
Memory allocation error.
Definition: XLALError.h:407
@ XLAL_EFAULT
Invalid pointer.
Definition: XLALError.h:408
@ XLAL_EFUNC
Internal function call failed bit: "or" this with existing error number.
Definition: XLALError.h:462
@ XLAL_EINVAL
Invalid argument.
Definition: XLALError.h:409
Vector of type CHAR*, ie 'strings', see DATATYPE-Vector types for more details.
Definition: LALDatatypes.h:82
Epoch relative to GPS epoch, see LIGOTimeGPS type for more details.
Definition: LALDatatypes.h:458
Possible choices the user may select for an enumeration or bitflag.