|
|
|
|
@ -8,7 +8,7 @@ |
|
|
|
|
* |
|
|
|
|
* |
|
|
|
|
* IDENTIFICATION |
|
|
|
|
* $PostgreSQL: pgsql/src/backend/utils/adt/bool.c,v 1.45 2009/01/01 17:23:49 momjian Exp $ |
|
|
|
|
* $PostgreSQL: pgsql/src/backend/utils/adt/bool.c,v 1.46 2009/03/09 14:34:34 petere Exp $ |
|
|
|
|
* |
|
|
|
|
*------------------------------------------------------------------------- |
|
|
|
|
*/ |
|
|
|
|
@ -20,6 +20,99 @@ |
|
|
|
|
#include "libpq/pqformat.h" |
|
|
|
|
#include "utils/builtins.h" |
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
* Try to interpret value as boolean value. Valid values are: true, |
|
|
|
|
* false, yes, no, on, off, 1, 0; as well as unique prefixes thereof. |
|
|
|
|
* If the string parses okay, return true, else false. |
|
|
|
|
* If okay and result is not NULL, return the value in *result. |
|
|
|
|
*/ |
|
|
|
|
bool |
|
|
|
|
parse_bool(const char *value, bool *result) |
|
|
|
|
{ |
|
|
|
|
return parse_bool_with_len(value, strlen(value), result); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
bool |
|
|
|
|
parse_bool_with_len(const char *value, size_t len, bool *result) |
|
|
|
|
{ |
|
|
|
|
switch (*value) |
|
|
|
|
{ |
|
|
|
|
case 't': |
|
|
|
|
case 'T': |
|
|
|
|
if (pg_strncasecmp(value, "true", len) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = true; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case 'f': |
|
|
|
|
case 'F': |
|
|
|
|
if (pg_strncasecmp(value, "false", len) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = false; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case 'y': |
|
|
|
|
case 'Y': |
|
|
|
|
if (pg_strncasecmp(value, "yes", len) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = true; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case 'n': |
|
|
|
|
case 'N': |
|
|
|
|
if (pg_strncasecmp(value, "no", len) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = false; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case 'o': |
|
|
|
|
case 'O': |
|
|
|
|
/* 'o' is not unique enough */ |
|
|
|
|
if (pg_strncasecmp(value, "on", (len > 2 ? len : 2)) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = true; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
else if (pg_strncasecmp(value, "off", (len > 2 ? len : 2)) == 0) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = false; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case '1': |
|
|
|
|
if (len == 1) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = true; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
case '0': |
|
|
|
|
if (len == 1) |
|
|
|
|
{ |
|
|
|
|
if (result) |
|
|
|
|
*result = false; |
|
|
|
|
return true; |
|
|
|
|
} |
|
|
|
|
break; |
|
|
|
|
default: |
|
|
|
|
break; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
*result = false; /* suppress compiler warning */ |
|
|
|
|
return false; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/*****************************************************************************
|
|
|
|
|
* USER I/O ROUTINES * |
|
|
|
|
*****************************************************************************/ |
|
|
|
|
@ -27,8 +120,8 @@ |
|
|
|
|
/*
|
|
|
|
|
* boolin - converts "t" or "f" to 1 or 0 |
|
|
|
|
* |
|
|
|
|
* Check explicitly for "true/false" and TRUE/FALSE, 1/0, YES/NO. |
|
|
|
|
* Reject other values. - thomas 1997-10-05 |
|
|
|
|
* Check explicitly for "true/false" and TRUE/FALSE, 1/0, YES/NO, ON/OFF. |
|
|
|
|
* Reject other values. |
|
|
|
|
* |
|
|
|
|
* In the switch statement, check the most-used possibilities first. |
|
|
|
|
*/ |
|
|
|
|
@ -38,6 +131,7 @@ boolin(PG_FUNCTION_ARGS) |
|
|
|
|
const char *in_str = PG_GETARG_CSTRING(0); |
|
|
|
|
const char *str; |
|
|
|
|
size_t len; |
|
|
|
|
bool result; |
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
* Skip leading and trailing whitespace |
|
|
|
|
@ -50,45 +144,8 @@ boolin(PG_FUNCTION_ARGS) |
|
|
|
|
while (len > 0 && isspace((unsigned char) str[len - 1])) |
|
|
|
|
len--; |
|
|
|
|
|
|
|
|
|
switch (*str) |
|
|
|
|
{ |
|
|
|
|
case 't': |
|
|
|
|
case 'T': |
|
|
|
|
if (pg_strncasecmp(str, "true", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(true); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
case 'f': |
|
|
|
|
case 'F': |
|
|
|
|
if (pg_strncasecmp(str, "false", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(false); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
case 'y': |
|
|
|
|
case 'Y': |
|
|
|
|
if (pg_strncasecmp(str, "yes", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(true); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
case '1': |
|
|
|
|
if (pg_strncasecmp(str, "1", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(true); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
case 'n': |
|
|
|
|
case 'N': |
|
|
|
|
if (pg_strncasecmp(str, "no", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(false); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
case '0': |
|
|
|
|
if (pg_strncasecmp(str, "0", len) == 0) |
|
|
|
|
PG_RETURN_BOOL(false); |
|
|
|
|
break; |
|
|
|
|
|
|
|
|
|
default: |
|
|
|
|
break; |
|
|
|
|
} |
|
|
|
|
if (parse_bool_with_len(str, len, &result)) |
|
|
|
|
PG_RETURN_BOOL(result); |
|
|
|
|
|
|
|
|
|
ereport(ERROR, |
|
|
|
|
(errcode(ERRCODE_INVALID_TEXT_REPRESENTATION), |
|
|
|
|
|