Codex found this during an algorithm-defect audit of the time codebase.
Audited revision: 8706e568aafcd4562fde792374b94b735ae53a0a.
Summary
Both %z parsing and the ISO 8601 timeOffsetFormat accept numeric timezone offsets without validating their hour/minute components. A minute field of 60 is normalized into an extra hour instead of being rejected.
Reproduction
parseTimeM False defaultTimeLocale "%z" "+2360" :: Maybe TimeZone
-- Just +2400
formatParseM (timeOffsetFormat ExtendedFormat) "+23:60"
-- Just +2400
formatParseM (timeOffsetFormat ExtendedFormat) "+24:01"
-- Just +2401
Expected
Malformed offsets should fail. In particular, the minute component must be in 00..59; the ISO parser should also enforce the permitted overall ISO 8601 offset range.
Actual
The parsers calculate hours * 60 + minutes, accepting invalid input as a different offset.
Affected code
lib/Data/Time/Format/Parse/Instances.hs: readTzOffset.
lib/Data/Time/Format/ISO8601.hs: timeOffsetFormat (digits2 plus unrestricted isoMap).
Codex found this during an algorithm-defect audit of the
timecodebase.Audited revision:
8706e568aafcd4562fde792374b94b735ae53a0a.Summary
Both
%zparsing and the ISO 8601timeOffsetFormataccept numeric timezone offsets without validating their hour/minute components. A minute field of60is normalized into an extra hour instead of being rejected.Reproduction
Expected
Malformed offsets should fail. In particular, the minute component must be in
00..59; the ISO parser should also enforce the permitted overall ISO 8601 offset range.Actual
The parsers calculate
hours * 60 + minutes, accepting invalid input as a different offset.Affected code
lib/Data/Time/Format/Parse/Instances.hs:readTzOffset.lib/Data/Time/Format/ISO8601.hs:timeOffsetFormat(digits2plus unrestrictedisoMap).