golang / go

The Go programming language
https://go.dev
BSD 3-Clause "New" or "Revised" License
123.26k stars 17.57k forks source link

x/image/bmp: NewNRGBA will panic when dealing with too large length and width #60885

Open pic4xiu opened 1 year ago

pic4xiu commented 1 year ago

What version of Go are you using (go version)?

❯ go version
go version go1.20.4 darwin/arm64

Does this issue reproduce with the latest release?

Yes

What operating system and processor architecture are you using (go env)?

go env Output
does not affect

What did you do?

package main

import (
    "bytes"
    "image"
    "os"

    "golang.org/x/image/bmp"
)

func main() {
    data := []byte("BM0000\x00\x00\x00\x006\x00\x00\x00(\x00\x00\x0000000000\x01\x00 \x00\x00\x00\x00\x0000000000000000000000")

    src, _, err := image.Decode(bytes.NewReader(data))
    if err != nil {
        panic(err)
    }
    file, err := os.Create("output.bmp")
    if err != nil {
        panic(err)
    }
    defer file.Close()

    err = bmp.Encode(file, src)
    if err != nil {
        panic(err)
    }
}

What did you expect to see?

Error returned: image size too large

What did you see instead?

❯ go run main.go
panic: runtime error: makeslice: len out of range

goroutine 1 [running]:
image.NewNRGBA({{0x3ee?, 0x24?}, {0x1400009ce68?, 0x280462c074?}})
        /usr/local/go/src/image/image.go:459 +0x64
golang.org/x/image/bmp.decodeNRGBA({0x10467e6e8, 0x14000092180}, {{0x10467e748?, 0x140000ac000?}, 0x1046703a0?, 0x104679980?}, 0x0, 0x0)
        /Users/*/go/pkg/mod/golang.org/x/image@v0.8.0/bmp/reader.go:89 +0x64
golang.org/x/image/bmp.Decode({0x10467e6e8, 0x14000092180})
        /Users/*/go/pkg/mod/golang.org/x/image@v0.8.0/bmp/reader.go:126 +0x64
image.Decode({0x10467e708?, 0x140000a01b0?})
        /usr/local/go/src/image/format.go:93 +0x8c
main.main()
        /Users/*/Desktop/src/cve/main.go:14 +0xbc
exit status 2

I tried to modify it to limit the length of the decodeNRGBA function, but it was only roughly completed. Need to know the size of maxAlloc in the runtime package. This is the fundamental solution to this bug

ianlancetaylor commented 1 year ago

CC @nigeltao

bcmills commented 1 year ago

See previously #58003 (CC @rolandshoemaker, @golang/security).

rolandshoemaker commented 1 year ago

Unlike https://github.com/golang/go/issues/58003, this is in Decode. Calling DecodeConfig, in this and generally, lets you know the dimensions of the image before attempting to decode it, which in this case are 808464432 x 808464432 (an image on the order of 600 petabytes).

Decode should probably(?) not be opportunistically attempting to preallocate the pixel slice (by calling image.NewRGBA), but since this is reliant on the user not being aware of the actual size of the image, we won't consider this a security issue.