aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Paquier <michael@paquier.xyz>2019-08-07 18:17:39 +0900
committerMichael Paquier <michael@paquier.xyz>2019-08-07 18:17:39 +0900
commitd16d241a55557352e09c9ffd6ab20548b066d193 (patch)
tree0ac5c9cfb474797666c16c549a93c6d1c2a8da2e
parent113b3d903b348a3c8ac92cdb0389d5ca779c197f (diff)
downloadpostgresql-d16d241a55557352e09c9ffd6ab20548b066d193.tar.gz
postgresql-d16d241a55557352e09c9ffd6ab20548b066d193.zip
Fix some incorrect parsing of time with time zone strings
When parsing a timetz string with a dynamic timezone abbreviation or a timezone not specified, it was possible to generate incorrect timestamps based on a date which uses some non-initialized variables if the input string did not specify fully a date to parse. This is already checked when a full timezone spec is included in the input string, but the two other cases mentioned above missed the same checks. This gets fixed by generating an error as this input is invalid, or in short when a date is not fully specified. Valgrind was complaining about this problem. Bug: #15910 Author: Alexander Lakhin Discussion: https://postgr.es/m/15910-2eba5106b9aa0c61@postgresql.org Backpatch-through: 9.4
-rw-r--r--src/backend/utils/adt/datetime.c6
-rw-r--r--src/test/regress/expected/timetz.out10
-rw-r--r--src/test/regress/sql/timetz.sql5
3 files changed, 21 insertions, 0 deletions
diff --git a/src/backend/utils/adt/datetime.c b/src/backend/utils/adt/datetime.c
index 7b585492200..a3e3c6daaf0 100644
--- a/src/backend/utils/adt/datetime.c
+++ b/src/backend/utils/adt/datetime.c
@@ -2301,6 +2301,9 @@ DecodeTimeOnly(char **field, int *ftype, int nf,
GetCurrentDateTime(tmp);
else
{
+ /* a date has to be specified */
+ if ((fmask & DTK_DATE_M) != DTK_DATE_M)
+ return DTERR_BAD_FORMAT;
tmp->tm_year = tm->tm_year;
tmp->tm_mon = tm->tm_mon;
tmp->tm_mday = tm->tm_mday;
@@ -2328,6 +2331,9 @@ DecodeTimeOnly(char **field, int *ftype, int nf,
GetCurrentDateTime(tmp);
else
{
+ /* a date has to be specified */
+ if ((fmask & DTK_DATE_M) != DTK_DATE_M)
+ return DTERR_BAD_FORMAT;
tmp->tm_year = tm->tm_year;
tmp->tm_mon = tm->tm_mon;
tmp->tm_mday = tm->tm_mday;
diff --git a/src/test/regress/expected/timetz.out b/src/test/regress/expected/timetz.out
index 33ff8e18c9d..482a3463b3c 100644
--- a/src/test/regress/expected/timetz.out
+++ b/src/test/regress/expected/timetz.out
@@ -19,6 +19,16 @@ INSERT INTO TIMETZ_TBL VALUES ('15:36:39 America/New_York');
ERROR: invalid input syntax for type time with time zone: "15:36:39 America/New_York"
LINE 1: INSERT INTO TIMETZ_TBL VALUES ('15:36:39 America/New_York');
^
+-- this should fail (timezone not specified without a date)
+INSERT INTO TIMETZ_TBL VALUES ('15:36:39 m2');
+ERROR: invalid input syntax for type time with time zone: "15:36:39 m2"
+LINE 1: INSERT INTO TIMETZ_TBL VALUES ('15:36:39 m2');
+ ^
+-- this should fail (dynamic timezone abbreviation without a date)
+INSERT INTO TIMETZ_TBL VALUES ('15:36:39 MSK m2');
+ERROR: invalid input syntax for type time with time zone: "15:36:39 MSK m2"
+LINE 1: INSERT INTO TIMETZ_TBL VALUES ('15:36:39 MSK m2');
+ ^
SELECT f1 AS "Time TZ" FROM TIMETZ_TBL;
Time TZ
----------------
diff --git a/src/test/regress/sql/timetz.sql b/src/test/regress/sql/timetz.sql
index c41686a5e2f..2ad4948e850 100644
--- a/src/test/regress/sql/timetz.sql
+++ b/src/test/regress/sql/timetz.sql
@@ -19,6 +19,11 @@ INSERT INTO TIMETZ_TBL VALUES ('2003-03-07 15:36:39 America/New_York');
INSERT INTO TIMETZ_TBL VALUES ('2003-07-07 15:36:39 America/New_York');
-- this should fail (the timezone offset is not known)
INSERT INTO TIMETZ_TBL VALUES ('15:36:39 America/New_York');
+-- this should fail (timezone not specified without a date)
+INSERT INTO TIMETZ_TBL VALUES ('15:36:39 m2');
+-- this should fail (dynamic timezone abbreviation without a date)
+INSERT INTO TIMETZ_TBL VALUES ('15:36:39 MSK m2');
+
SELECT f1 AS "Time TZ" FROM TIMETZ_TBL;