debug/dwarf: don't crash on negative line file index
A malformed DWARF line table can cause a DW_LNS_set_file operand to
overflow when converted to int, producing a negative file index
resulting in a panic due to an out-of-bounds slice access in updateFile.
For #47653
diff --git a/src/debug/dwarf/fuzz_test.go b/src/debug/dwarf/fuzz_test.go
index bc342b0..e653520 100644
--- a/src/debug/dwarf/fuzz_test.go
+++ b/src/debug/dwarf/fuzz_test.go
@@ -14,6 +14,35 @@
f.Skip("Skipping in short mode")
}
+ // A DWARF 4 compile unit with a line program containing a
+ // DW_LNS_set_file instruction with a file index of math.MaxUint64.
+ f.Add(
+ []byte{
+ 1, 0x11, 0,
+ 0x10, 0x17,
+ 0, 0,
+ 0,
+ },
+ []byte{
+ 0x0c, 0, 0, 0,
+ 4, 0,
+ 0, 0, 0, 0,
+ 8,
+ 1,
+ 0, 0, 0, 0,
+ },
+ []byte{
+ 0x25, 0, 0, 0,
+ 4, 0,
+ 0x14, 0, 0, 0,
+ 1, 1, 1, 0, 1, 13,
+ 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 1,
+ 0, 0,
+ 4,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 1,
+ },
+ )
+
f.Fuzz(func(t *testing.T, abbrev, info, line []byte) {
d, err := dwarf.New(abbrev, nil, nil, info, line, nil, nil, nil)
if err != nil {
diff --git a/src/debug/dwarf/line.go b/src/debug/dwarf/line.go
index 3811416..f6fe08e 100644
--- a/src/debug/dwarf/line.go
+++ b/src/debug/dwarf/line.go
@@ -465,7 +465,7 @@
// updateFile updates r.state.File after r.fileIndex has
// changed or r.fileEntries has changed.
func (r *LineReader) updateFile() {
- if r.fileIndex < len(r.fileEntries) {
+ if r.fileIndex >= 0 && r.fileIndex < len(r.fileEntries) {
r.state.File = r.fileEntries[r.fileIndex]
} else {
r.state.File = nil
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Code-Review | +2 |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Auto-Submit | +1 |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Code-Review | +1 |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
| Code-Review | +1 |
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |
1 is the latest approved patch-set.
The change was submitted with unreviewed changes in the following files:
```
The name of the file: src/debug/dwarf/fuzz_test.go
Insertions: 73, Deletions: 0.
@@ -6,6 +6,11 @@
import (
"debug/dwarf"
+ "debug/elf"
+ "debug/macho"
+ "os"
+ "path/filepath"
+ "strings"
"testing"
)
@@ -14,6 +19,79 @@
f.Skip("Skipping in short mode")
}
+ dwarfSuffix := func(name string) string {
+ switch {
+ // ELF prefixes, see dwarfSuffix in debug/elf.DWARF
+ case strings.HasPrefix(name, ".debug_"):
+ return name[7:]
+ case strings.HasPrefix(name, ".zdebug_"):
+ return name[8:]
+ // machO prefixes, see dwarfSuffix in debug/macho.DWARF
+ case strings.HasPrefix(name, "__debug_"):
+ return name[8:]
+ case strings.HasPrefix(name, "__zdebug_"):
+ return name[9:]
+ default:
+ return ""
+ }
+ }
+
+ testdata, err := os.ReadDir("testdata")
+ if err != nil {
+ f.Fatalf("failed to read testdata directory: %s", err)
+ }
+ for _, de := range testdata {
+ if de.IsDir() {
+ continue
+ }
+
+ var abbrev, info, line []byte
+
+ ext := filepath.Ext(de.Name())
+ name := filepath.Join("testdata", de.Name())
+
+ switch {
+ case strings.HasPrefix(ext, ".elf"):
+ e, err := elf.Open(name)
+ if err != nil {
+ f.Fatal(err)
+ }
+
+ for _, s := range e.Sections {
+ switch dwarfSuffix(s.Name) {
+ case "abbrev":
+ abbrev, _ = s.Data()
+ case "info":
+ info, _ = s.Data()
+ case "line":
+ line, _ = s.Data()
+ }
+ }
+ case strings.HasPrefix(ext, ".macho"):
+ m, err := macho.Open(name)
+ if err != nil {
+ f.Fatal(err)
+ }
+
+ for _, s := range m.Sections {
+ switch dwarfSuffix(s.Name) {
+ case "abbrev":
+ abbrev, _ = s.Data()
+ case "info":
+ info, _ = s.Data()
+ case "line":
+ line, _ = s.Data()
+ }
+ }
+ default:
+ continue
+ }
+
+ if len(abbrev) > 0 || len(info) > 0 || len(line) > 0 {
+ f.Add(abbrev, info, line)
+ }
+ }
+
// A DWARF 4 compile unit with a line program containing a
// DW_LNS_set_file instruction with a file index of math.MaxUint64.
f.Add(
```
debug/dwarf: don't crash on negative line file index
A malformed DWARF line table can cause a DW_LNS_set_file operand to
overflow when converted to int, producing a negative file index
resulting in a panic due to an out-of-bounds slice access in updateFile.
For #47653
Fixes #81184
| Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. |