x/website/internal/codewalk: backward character offsets panic at EOF
- Dominant language
- Go
- Stars
- 139k
- Forks
- 19.4k
- PR merge metrics
- PR metrics pending
Description
### Go version
go1.25.6 darwin/arm64
### Output of `go env` in your module/workspace:
```shell
AR='ar'
CC='clang'
CGO_CFLAGS='-O2 -g'
CGO_CPPFLAGS=''
CGO_CXXFLAGS='-O2 -g'
CGO_ENABLED='1'
CGO_FFLAGS='-O2 -g'
CGO_LDFLAGS='-O2 -g'
CXX='clang++'
GCCGO='gccgo'
GO111MODULE=''
GOARCH='arm64'
GOARM64='v8.0'
GOAUTH='netrc'
GOBIN='/Users/mac/go/bin'
GOCACHE='/Users/mac/Library/Caches/go-build'
GOCACHEPROG=''
GODEBUG=''
GOENV='/Users/mac/Library/Application Support/go/env'
GOEXE=''
GOEXPERIMENT=''
GOFIPS140='off'
GOFLAGS=''
GOGCCFLAGS='-fPIC -arch arm64 -pthread -fno-caret-diagnostics -Qunused-arguments -fmessage-length=0 -ffile-prefix-map=/var/folders/66/63zhln_s7wz_fn6wsbh3t2000000gn/T/go-build4005551914=/tmp/go-build -gno-record-gcc-switches -fno-common'
GOHOSTARCH='arm64'
GOHOSTOS='darwin'
GOINSECURE=''
GOMOD='/dev/null'
GOMODCACHE='/Users/mac/go/pkg/mod'
GONOPROXY=''
GONOSUMDB=''
GOOS='darwin'
GOPATH='/Users/mac/go'
GOPRIVATE=''
GOPROXY=''
GOROOT='/usr/local/go'
GOSUMDB='sum.golang.org'
GOTELEMETRY='local'
GOTELEMETRYDIR='/Users/mac/Library/Application Support/go/telemetry'
GOTMPDIR=''
GOTOOLCHAIN='auto'
GOTOOLDIR='/usr/local/go/pkg/tool/darwin_arm64'
GOVCS=''
GOVERSION='go1.25.6'
GOWORK=''
PKG_CONFIG='pkg-config'
```
### What did you do?
`internal/codewalk` supports sam-style addresses, including character offsets such as `+#3`, `-#2`, and `$`.
The following address starts at EOF and moves backward by one UTF-8 character:
```go
data := []byte("é")
lo, hi, err := addrToByteRange("$-#1", 0, data)
```
Another reproducer is:
```go
data := []byte("é好x")
lo, hi, err := addrToByteRange("#2-#1", 0, data)
```
### What did you see happen?
`$-#1` panics with an index-out-of-range error.
The backward character scan initializes `pos` to `lo` and reads `data[pos]` before decrementing it. At EOF, `pos == len(data)`, so the first iteration accesses `data[len(data)]`.
Away from EOF, the same ordering checks the byte at the current position instead of the preceding byte. For `#2-#1` on `é好x`, the current implementation returns byte offset 4, which is inside the UTF-8 encoding of `好`.
The scan should decrement `pos` before checking whether the byte is a UTF-8 continuation byte. Tests should cover both EOF and multibyte UTF-8 input.
### What did you expect to see?
For $-#1, I expected (lo, hi, err) to be (0, 0, nil).
For #2-#1, I expected (lo, hi, err) to be (2, 2, nil), pointing to the first byte of 好.
Contributor guide
Research direction
Start at addrToByteRange in x/website/internal/codewalk and trace the backward character-offset scan, then run the package tests. Add coverage for the $-#1 and #2-#1 reproducers with multibyte UTF-8 input; done means both return (0, 0, nil) and (2, 2, nil) without panicking.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- go
- Domain
- documentation
- Issue type
- Bug
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Activity status
- Active
- Clarity
- Clearly specified
- Newbie friendliness
- 84/100