dotnet / dotnet/fsharp

Array and string slicing throw when the finish bound is near Int32.MinValue

Open
#20,530 0 comments 0 reactions 0 assignees View on GitHub
Needs-Triage
Dominant language
F#
Stars
4.3k
Forks
876
Avg merge
4d 11h
Merged PRs (30d)
131

Description

Tolerant slicing ([RFC FS-1077](https://github.com/fsharp/fslang-design/blob/main/FSharp-5.0/FS-1077-tolerant-slicing.md)) returns an empty result when `finish < start`. On arrays and strings the length `finish - start + 1` overflows when `finish` is close to `Int32.MinValue`, and the slice throws instead.

```fsharp
let m = System.Int32.MinValue
[| 1..5 |][3..m] // OutOfMemoryException
(Array2D.init 5 5 (+))[3..m, *] // OutOfMemoryException
"hello"[3..m] // ArgumentOutOfRangeException
[ 1..5 ][3..m] // [], lists are correct
[| 1..5 |][3..(m + 10)] // [||], no overflow
```

**Expected:** an empty array or string, as for lists.

**Cause:** [`GetArraySlice`](https://github.com/dotnet/fsharp/blob/17f8eb7d0691d30d6fc0dbcc7977ac15f9e7d5d2/src/FSharp.Core/prim-types.fs#L6277-L6279) passes `finish - start + 1` to `GetArraySub`. With `start = 3` and `finish = Int32.MinValue` the result wraps to a large positive length. [`GetStringSlice`](https://github.com/dotnet/fsharp/blob/17f8eb7d0691d30d6fc0dbcc7977ac15f9e7d5d2/src/FSharp.Core/prim-types.fs#L6704) and the 2D–4D slicers use the same arithmetic. Comparing `finish < start` before subtracting avoids it: after `ComputeSlice`, `finish - start + 1` cannot overflow when `finish >= start`.

Found while checking the bound arithmetic for RFC FS-1351 (fsharp/fslang-design#849). SDK 11.0.100-rc.1.26420.103.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Contributor guide

Open the contributing guide

Research direction

Start in src/FSharp.Core/prim-types.fs at GetArraySlice and GetStringSlice, then inspect ComputeSlice, GetArraySub, and the 2D–4D slicers that use the same length arithmetic. Reproduce the examples with Int32.MinValue and verify that array, string, and multidimensional slices return empty results without throwing, while normal and list slicing behavior remains unchanged.

Written by the indexing model from the issue text.

Assessment

Tech stack
fsharp
Domain
compilers
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Active
Clarity
Clearly specified
Newbie friendliness
78/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.