diff --git a/pkg/dwarf/line/line_parser.go b/pkg/dwarf/line/line_parser.go index b69c502ef2..dd6fbb782f 100644 --- a/pkg/dwarf/line/line_parser.go +++ b/pkg/dwarf/line/line_parser.go @@ -4,6 +4,7 @@ import ( "bytes" "encoding/binary" "path/filepath" + "strings" "github.com/go-delve/delve/pkg/dwarf/util" ) @@ -34,9 +35,12 @@ type DebugLineInfo struct { // lastMachineCache[pc] is a state machine stopped at an address after pc lastMachineCache map[uint64]*StateMachine - + // staticBase is the address at which the executable is loaded, 0 for non-PIEs staticBase uint64 + + // if normalizeBackslash is true all backslashes (\) will be converted into forward slashes (/) + normalizeBackslash bool } type FileEntry struct { @@ -49,7 +53,7 @@ type FileEntry struct { type DebugLines []*DebugLineInfo // ParseAll parses all debug_line segments found in data -func ParseAll(data []byte, logfn func(string, ...interface{}), staticBase uint64) DebugLines { +func ParseAll(data []byte, logfn func(string, ...interface{}), staticBase uint64, normalizeBackslash bool) DebugLines { var ( lines = make(DebugLines, 0) buf = bytes.NewBuffer(data) @@ -57,7 +61,7 @@ func ParseAll(data []byte, logfn func(string, ...interface{}), staticBase uint64 // We have to parse multiple file name tables here. for buf.Len() > 0 { - lines = append(lines, Parse("", buf, logfn, staticBase)) + lines = append(lines, Parse("", buf, logfn, staticBase, normalizeBackslash)) } return lines @@ -65,7 +69,7 @@ func ParseAll(data []byte, logfn func(string, ...interface{}), staticBase uint64 // Parse parses a single debug_line segment from buf. Compdir is the // DW_AT_comp_dir attribute of the associated compile unit. -func Parse(compdir string, buf *bytes.Buffer, logfn func(string, ...interface{}), staticBase uint64) *DebugLineInfo { +func Parse(compdir string, buf *bytes.Buffer, logfn func(string, ...interface{}), staticBase uint64, normalizeBackslash bool) *DebugLineInfo { dbl := new(DebugLineInfo) dbl.Logf = logfn dbl.staticBase = staticBase @@ -76,6 +80,7 @@ func Parse(compdir string, buf *bytes.Buffer, logfn func(string, ...interface{}) dbl.stateMachineCache = make(map[uint64]*StateMachine) dbl.lastMachineCache = make(map[uint64]*StateMachine) + dbl.normalizeBackslash = normalizeBackslash parseDebugLinePrologue(dbl, buf) parseIncludeDirs(dbl, buf) @@ -139,6 +144,10 @@ func readFileEntry(info *DebugLineInfo, buf *bytes.Buffer, exitOnEmptyPath bool) return entry } + if info.normalizeBackslash { + entry.Path = strings.Replace(entry.Path, "\\", "/", -1) + } + entry.DirIdx, _ = util.DecodeULEB128(buf) entry.LastModTime, _ = util.DecodeULEB128(buf) entry.Length, _ = util.DecodeULEB128(buf) diff --git a/pkg/dwarf/line/line_parser_test.go b/pkg/dwarf/line/line_parser_test.go index dd3b5f58ed..b5813cd0e4 100644 --- a/pkg/dwarf/line/line_parser_test.go +++ b/pkg/dwarf/line/line_parser_test.go @@ -67,7 +67,7 @@ const ( func testDebugLinePrologueParser(p string, t *testing.T) { data := grabDebugLineSection(p, t) - debugLines := ParseAll(data, nil, 0) + debugLines := ParseAll(data, nil, 0, true) mainFileFound := false @@ -164,7 +164,7 @@ func BenchmarkLineParser(b *testing.B) { b.ResetTimer() for i := 0; i < b.N; i++ { - _ = ParseAll(data, nil, 0) + _ = ParseAll(data, nil, 0, true) } } @@ -179,7 +179,7 @@ func loadBenchmarkData(tb testing.TB) DebugLines { tb.Fatal("Could not read test data", err) } - return ParseAll(data, nil, 0) + return ParseAll(data, nil, 0, true) } func BenchmarkStateMachine(b *testing.B) { diff --git a/pkg/dwarf/line/state_machine_test.go b/pkg/dwarf/line/state_machine_test.go index 6e9e79eb24..3a36d183d3 100644 --- a/pkg/dwarf/line/state_machine_test.go +++ b/pkg/dwarf/line/state_machine_test.go @@ -80,7 +80,7 @@ func TestGrafana(t *testing.T) { } cuname, _ := e.Val(dwarf.AttrName).(string) - lineInfo := Parse(e.Val(dwarf.AttrCompDir).(string), debugLineBuffer, t.Logf, 0) + lineInfo := Parse(e.Val(dwarf.AttrCompDir).(string), debugLineBuffer, t.Logf, 0, false) sm := newStateMachine(lineInfo, lineInfo.Instructions) lnrdr, err := data.LineReader(e) diff --git a/pkg/proc/bininfo.go b/pkg/proc/bininfo.go index 73a5d45211..4745132472 100644 --- a/pkg/proc/bininfo.go +++ b/pkg/proc/bininfo.go @@ -1327,7 +1327,7 @@ func (bi *BinaryInfo) loadDebugInfoMaps(image *Image, debugLineBytes []byte, wg logger.Printf(fmt, args) } } - cu.lineInfo = line.Parse(compdir, bytes.NewBuffer(debugLineBytes[lineInfoOffset:]), logfn, image.StaticBase) + cu.lineInfo = line.Parse(compdir, bytes.NewBuffer(debugLineBytes[lineInfoOffset:]), logfn, image.StaticBase, bi.GOOS == "windows") } cu.producer, _ = entry.Val(dwarf.AttrProducer).(string) if cu.isgo && cu.producer != "" {