27 #include <lal/StringInput.h>
28 #include <lal/AVFactories.h>
29 #include <lal/StringVector.h>
30 #include <lal/LALConstants.h>
31 #include <lal/LALString.h>
32 #include <lal/TranslateMJD.h>
33 #include <lal/TranslateAngles.h>
35 #include <lal/UserInputParse.h>
39 #define LAL_sINT4_MAX LAL_INT8_C(2147483647)
40 #define LAL_sINT8_MAX LAL_INT8_C(9223372036854775807)
42 #define MYMAX(x,y) ( (x) > (y) ? (x) : (y) )
43 #define MYMIN(x,y) ( (x) < (y) ? (x) : (y) )
59 long long valLLong = strtoll ( valString, &endptr, base10 );
61 XLAL_CHECK ( (*endptr) ==
'\0',
XLAL_EFAILED,
"strtoll(): trailing garbage '%s' found after int-conversion of '%s'\n", endptr, valString );
64 if (
sizeof(valLLong) >
sizeof(
INT8) ) {
69 (*valINT8) = (
INT8)valLLong;
92 (*valINT4) = (
INT4)valINT8;
103 const char *valString
111 unsigned long long valULLong = strtoull ( valString, &endptr, base10 );
113 XLAL_CHECK ( (*endptr) ==
'\0',
XLAL_EFAILED,
"strtoll(): trailing garbage '%s' found after int-conversion of '%s'\n", endptr, valString );
116 long long valLLong = strtoll ( valString, &endptr, base10 );
120 if (
sizeof(valULLong) >
sizeof(
UINT8) ) {
125 (*valUINT8) = (
UINT8)valULLong;
136 const char *valString
148 (*valUINT4) = (
UINT4)valUINT8;
159 const char *valString
166 double valDouble = strtod ( valString, &endptr );
168 XLAL_CHECK ( (*endptr) ==
'\0',
XLAL_EFAILED,
"strtod(): trailing garbage '%s' found after double-conversion of '%s'\n", endptr, valString );
170 (*valREAL8) = (
REAL8)valDouble;
180 const char *valString
187 float valFloat = strtof ( valString, &endptr );
189 XLAL_CHECK ( (*endptr) ==
'\0',
XLAL_EFAILED,
"strtof(): trailing garbage '%s' found after float-conversion of '%s'\n", endptr, valString );
191 (*valREAL4) = (
REAL4)valFloat;
205 const char *valString
209 XLAL_CHECK ( !isspace(valString[0]),
XLAL_EINVAL,
"No initial whitespace allowed in input string '%s'\n", valString );
212 strncpy ( buf, valString,
sizeof(buf)-1 );
216 if ( valString[0] ==
'-' ) {
219 char *point = strchr ( buf,
'.' );
224 char fracString[256] =
"0.";
225 strcat ( fracString+2, point+1);
249 const char *valString
255 char *valStringLower;
257 strcpy ( valStringLower, valString );
261 if ( !strcmp(valStringLower,
"yes") || !strcmp(valStringLower,
"true") || !strcmp(valStringLower,
"1") )
265 else if ( !strcmp(valStringLower,
"no") || !strcmp(valStringLower,
"false") || !strcmp(valStringLower,
"0") )
272 XLAL_ERROR (
XLAL_EINVAL,
"Illegal bool-string '%s', needs to be one of {'yes', 'true', '1'} or {'no', 'false', '0'} (case-insensitive)\n", valString );
288 const char *valString
315 const char *valString
321 strncpy ( buf, valString,
sizeof(buf)-1 );
327 if ( (postfix = strstr ( buf,
"MJD" )) != NULL )
329 XLAL_CHECK ( postfix[3] == 0,
XLAL_EINVAL,
"Input '%s' contains trailing characters after units 'MJD': must be of form 'xxx.yyyMJD'\n", valString );
333 else if ( (postfix = strstr ( buf,
"GPS" )) != NULL )
335 XLAL_CHECK ( postfix[3] == 0,
XLAL_EINVAL,
"Input '%s' contains trailing characters after units 'GPS': must be of form 'xxx.yyy' or 'xxx.yyyGPS'\n", valString );
366 const char *valString
373 if ( (colon = strchr ( valString,
':' )) != NULL )
393 const char *valString
400 if ( (colon = strchr ( valString,
':' )) != NULL )
420 memset(part[0], 0,
sizeof(part[0]));
421 strncpy(part[0], str,
sizeof(part[0]) - 1);
422 memset(part[1], 0,
sizeof(part[1]));
423 strncpy(part[1], str,
sizeof(part[1]) - 1);
424 const int defT[2][2] = {{1, 0}, {0, 1}};
425 memcpy(T, defT,
sizeof(defT));
432 {
',', { {1, 0}, {0, 1} } },
433 {
'/', { {1, 0}, {1, 1} } },
434 {
'~', { {1, -1}, {1, 1} } },
441 const char *found = strchr(str, syntaxes[i].sep);
445 memset(part[0], 0,
sizeof(part[0]));
446 strncpy(part[0], str,
MYMIN((
size_t)(found - str),
sizeof(part[0]) - 1));
447 XLAL_CHECK( strlen(part[0]) > 0,
XLAL_EINVAL,
"Input '%s' contains no value before range separator '%c'", str, syntaxes[i].sep );
450 memset(part[1], 0,
sizeof(part[1]));
451 strncpy(part[1], found + 1,
sizeof(part[1]) - 1);
452 XLAL_CHECK( strlen(part[1]) > 0,
XLAL_EINVAL,
"Input '%s' contains no value after range separator '%c'", str, syntaxes[i].sep );
455 memcpy(T, syntaxes[i].T,
sizeof(syntaxes[i].T));
475 const char *valString
491 real8Range[0] = T[0][0] * val[0] + T[0][1] * val[1];
492 real8Range[1] = T[1][0] * val[0] + T[1][1] * val[1];
495 if (real8Range[0] > real8Range[1]) {
496 const REAL8 tmp = real8Range[0];
497 real8Range[0] = real8Range[1];
512 const char *valString
528 int4Range[0] = T[0][0] * val[0] + T[0][1] * val[1];
529 int4Range[1] = T[1][0] * val[0] + T[1][1] * val[1];
532 if (int4Range[0] > int4Range[1]) {
533 const INT4 tmp = int4Range[0];
534 int4Range[0] = int4Range[1];
550 const char *valString
570 if (
XLALGPSCmp(&gpsRange[0], &gpsRange[1]) > 0) {
572 gpsRange[0] = gpsRange[1];
588 const char *valString
604 rajRange[0] = T[0][0] * val[0] + T[0][1] * val[1];
605 rajRange[1] = T[1][0] * val[0] + T[1][1] * val[1];
608 if (rajRange[0] > rajRange[1]) {
609 const REAL8 tmp = rajRange[0];
610 rajRange[0] = rajRange[1];
626 const char *valString
642 decjRange[0] = T[0][0] * val[0] + T[0][1] * val[1];
643 decjRange[1] = T[1][0] * val[0] + T[1][1] * val[1];
646 if (decjRange[0] > decjRange[1]) {
647 const REAL8 tmp = decjRange[0];
648 decjRange[0] = decjRange[1];
664 const char *valString
676 if ((*enumData)[i].val >= 0 && (*enumData)[i].name != NULL) {
678 *valEnum = (*enumData)[i].val;
697 const char *valString
719 for (
size_t j = 0; j < valStringNames->
length; ++j ) {
722 if ((*flagData)[i].val > 0 && (*flagData)[i].name != NULL) {
724 valFlag_j = (*flagData)[i].val;
730 *valFlag |= valFlag_j;
764 CHAR opening_quote = 0;
765 CHAR closing_quote = 0;
766 UINT4 inlen = strlen ( valStr );
768 if ( (valStr[0] ==
'\'') || (valStr[0] ==
'\"') ) {
769 opening_quote = valStr[0];
771 if ( (inlen >= 2) && ( (valStr[inlen-1] ==
'\'') || (valStr[inlen-1] ==
'\"') ) ) {
772 closing_quote = valStr[inlen-1];
776 XLAL_CHECK ( opening_quote == closing_quote,
XLAL_EINVAL,
"Unmatched quotes in string [%s]\n", valStr );
778 const CHAR *start = valStr;
779 UINT4 outlen = inlen;
788 strncpy ( ret, start, outlen );
806 const CHAR *valString
815 const char *start = valString;
830 if ( !inQuotes && ((*tmp) ==
',') ) {
835 if ( (*tmp) ==
'\'' || (*tmp) ==
'\"' )
839 }
else if ( inQuotes == (*tmp) ) {
845 }
while ( (*tmp) != 0 );
848 len = strlen ( start );
860 }
while ( ( (*tmp) != 0) && ( *(start = tmp + 1) != 0 ) );
873 #define DEFN_XLALParseStringValueAsVector(CTYPE) \
874 DECL_XLALParseStringValueAsVector(CTYPE) \
876 XLAL_CHECK ( (valString != NULL) && (strlen(valString) > 0), XLAL_EINVAL ); \
877 XLAL_CHECK ( (vect != NULL) && (*vect == NULL) , XLAL_EINVAL ); \
880 LALStringVector *strVect = NULL; \
881 XLAL_CHECK ( XLALParseStringValueAsSTRINGVector ( &strVect, valString ) == XLAL_SUCCESS, XLAL_EFUNC ); \
882 UINT4 numElements = strVect->length; \
885 CTYPE##Vector *ret; \
886 XLAL_CHECK ( (ret = XLALCreate##CTYPE##Vector ( numElements )) != NULL, XLAL_EFUNC ); \
889 for ( UINT4 i = 0; i < numElements; i ++ ) \
891 XLAL_CHECK ( XLALParseStringValueAs##CTYPE ( &(ret->data[i]), strVect->data[i] ) == XLAL_SUCCESS, XLAL_EFUNC ); \
894 XLALDestroyStringVector ( strVect ); \
896 return XLAL_SUCCESS; \
#define XLAL_BILLION_REAL8
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).
#define XLAL_LAST_ELEM(x)
MACRO to access the last element in a fixed-size array.
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 XLALRealloc(p, n)
int XLALStringToLowerCase(char *string)
Turn a string in-place into lowercase without using locale-dependent functions.
int XLALStringCaseCompare(const char *s1, const char *s2)
Compare two strings, ignoring case and without using locale-dependent functions.
char * XLALDeblankString(const CHAR *start, UINT4 len)
Copy (and allocate) string from 'start' with length 'len', removing all starting- and trailing blanks...
void XLALDestroyStringVector(LALStringVector *vect)
XLAL-interface: Free a string-vector ;)
LALStringVector * XLALParseStringVector(const char *string, const char *delim)
Parse 'string' into a string vector of tokens, delimited by the characters 'delim'.
int XLALTranslateHMStoRAD(REAL8 *radians, const CHAR *hms)
Translate a string representing an angle in the form "hours:minutes:seconds" into radians.
int XLALTranslateDMStoRAD(REAL8 *radians, const CHAR *dms)
Translate a string representing an angle in the form "degrees:minutes:seconds" into radians.
LIGOTimeGPS * XLALTranslateStringMJDTTtoGPS(LIGOTimeGPS *gps, const char *mjdString)
Parse and convert given string representing MJD(TT) time into LIGOTimeGPS gps time,...
#define XLAL_ERROR(...)
Macro to invoke a failure from a XLAL routine returning an integer.
#define XLAL_CHECK(assertion,...)
Macro to test an assertion and invoke a failure if it is not true in a function that returns an integ...
#define XLAL_CHECK_FAIL(assertion,...)
Macro to test an assertion and invoke a failure if it is not true by jumping to a XLAL_FAIL label.
@ XLAL_ENOMEM
Memory allocation error.
@ XLAL_SUCCESS
Success return value (not an error number)
@ XLAL_EFAULT
Invalid pointer.
@ XLAL_EFUNC
Internal function call failed bit: "or" this with existing error number.
@ XLAL_EDOM
Input domain error.
@ XLAL_EINVAL
Invalid argument.
@ XLAL_EFAILED
Generic failure.
@ XLAL_FAILURE
Failure return value (not an error number)
int XLALGPSCmp(const LIGOTimeGPS *t0, const LIGOTimeGPS *t1)
Compares two GPS times.
LIGOTimeGPS * XLALGPSSet(LIGOTimeGPS *epoch, INT4 gpssec, INT8 gpsnan)
Sets GPS time given GPS integer seconds and residual nanoseconds.
LIGOTimeGPS * XLALINT8NSToGPS(LIGOTimeGPS *epoch, INT8 ns)
Converts nano seconds stored as an INT8 to GPS time.
INT8 XLALGPSToINT8NS(const LIGOTimeGPS *epoch)
Converts GPS time to nano seconds stored as an INT8.
Vector of type CHAR*, ie 'strings', see DATATYPE-Vector types for more details.
UINT4 length
Number of elements in array.
CHAR ** data
Pointer to the data array.
Epoch relative to GPS epoch, see LIGOTimeGPS type for more details.
Possible choices the user may select for an enumeration or bitflag.