diff --git a/src/Http/Headers/src/SetCookieHeaderValue.cs b/src/Http/Headers/src/SetCookieHeaderValue.cs index 359e6014dae2..967d959d0016 100644 --- a/src/Http/Headers/src/SetCookieHeaderValue.cs +++ b/src/Http/Headers/src/SetCookieHeaderValue.cs @@ -587,6 +587,16 @@ private static int GetSetCookieLength(StringSegment input, int startIndex, out S maxAge = -maxAge; } + // Check if maxAge would cause TimeSpan.FromSeconds to overflow + // TimeSpan.MaxValue.TotalSeconds is approximately 922337203685.4775 + const long MaxTimeSpanSeconds = 922337203685L; + const long MinTimeSpanSeconds = -922337203685L; + if (maxAge is > MaxTimeSpanSeconds or < MinTimeSpanSeconds) + { + // MaxAge value would overflow TimeSpan, abort + return 0; + } + result.MaxAge = TimeSpan.FromSeconds(maxAge); offset += itemLength; } diff --git a/src/Http/Headers/test/SetCookieHeaderValueTest.cs b/src/Http/Headers/test/SetCookieHeaderValueTest.cs index eff008809559..0d14851896b5 100644 --- a/src/Http/Headers/test/SetCookieHeaderValueTest.cs +++ b/src/Http/Headers/test/SetCookieHeaderValueTest.cs @@ -486,4 +486,30 @@ public void SetCookieHeaderValue_TryParseStrictList_FailsForAnyInvalidValues( Assert.Null(results); Assert.False(result); } + + [Theory] + [InlineData("name=value; max-age=922337203686")] // One more than TimeSpan.MaxValue.TotalSeconds + [InlineData("name=value; max-age=999999999999999999999")] // Much larger value + [InlineData("name=value; max-age=-922337203686")] // Negative overflow + public void SetCookieHeaderValue_TryParse_MaxAgeOverflow_ReturnsFalse(string value) + { + // Should return false instead of throwing ArgumentOutOfRangeException + bool result = SetCookieHeaderValue.TryParse(value, out var parsedValue); + Assert.False(result); + Assert.Null(parsedValue); + } + + [Theory] + [InlineData("name=value; max-age=922337203685")] // Max valid value + [InlineData("name=value; max-age=-922337203685")] // Min valid value + [InlineData("name=value; max-age=0")] // Zero + [InlineData("name=value; max-age=86400")] // One day in seconds + public void SetCookieHeaderValue_TryParse_MaxAgeValid_ReturnsTrue(string value) + { + // Should successfully parse valid max-age values + bool result = SetCookieHeaderValue.TryParse(value, out var parsedValue); + Assert.True(result); + Assert.NotNull(parsedValue); + Assert.NotNull(parsedValue!.MaxAge); + } }