ソースを参照

Merge pull request #70 from rauls5382/procmaps

Handle memory maps generated by logging
Raul Silvera 8 年 前
コミット
ecd093a0ce
共有1 個のファイルを変更した36 個の追加22 個の削除を含む
  1. 36
    22
      profile/legacy_profile.go

+ 36
- 22
profile/legacy_profile.go ファイルの表示

@@ -509,7 +509,7 @@ func parseHeap(b []byte) (p *Profile, err error) {
509 509
 			continue
510 510
 		}
511 511
 
512
-		if sectionTrigger(line) != unrecognizedSection {
512
+		if isMemoryMapSentinel(line) {
513 513
 			break
514 514
 		}
515 515
 
@@ -837,7 +837,7 @@ func parseThread(b []byte) (*Profile, error) {
837 837
 	if m := threadzStartRE.FindStringSubmatch(line); m != nil {
838 838
 		// Advance over initial comments until first stack trace.
839 839
 		for s.Scan() {
840
-			if line = s.Text(); sectionTrigger(line) != unrecognizedSection || strings.HasPrefix(line, "-") {
840
+			if line = s.Text(); isMemoryMapSentinel(line) || strings.HasPrefix(line, "-") {
841 841
 				break
842 842
 			}
843 843
 		}
@@ -853,7 +853,7 @@ func parseThread(b []byte) (*Profile, error) {
853 853
 
854 854
 	locs := make(map[uint64]*Location)
855 855
 	// Recognize each thread and populate profile samples.
856
-	for sectionTrigger(line) == unrecognizedSection {
856
+	for !isMemoryMapSentinel(line) {
857 857
 		if strings.HasPrefix(line, "---- no stack trace for") {
858 858
 			line = ""
859 859
 			break
@@ -944,12 +944,12 @@ func parseThreadSample(s *bufio.Scanner) (nextl string, addrs []uint64, err erro
944 944
 // parseAdditionalSections parses any additional sections in the
945 945
 // profile, ignoring any unrecognized sections.
946 946
 func parseAdditionalSections(s *bufio.Scanner, p *Profile) error {
947
-	for sectionTrigger(s.Text()) != memoryMapSection && s.Scan() {
947
+	for !isMemoryMapSentinel(s.Text()) && s.Scan() {
948 948
 	}
949 949
 	if err := s.Err(); err != nil {
950 950
 		return err
951 951
 	}
952
-	return p.parseMemoryMapFromScanner(s)
952
+	return p.ParseMemoryMapFromScanner(s)
953 953
 }
954 954
 
955 955
 // ParseProcMaps parses a memory map in the format of /proc/self/maps.
@@ -964,12 +964,19 @@ func ParseProcMaps(rd io.Reader) ([]*Mapping, error) {
964 964
 func parseProcMapsFromScanner(s *bufio.Scanner) ([]*Mapping, error) {
965 965
 	var mapping []*Mapping
966 966
 
967
+	// If the memory-map sentinel is at column X, assume memory mappings
968
+	// also start at X. This is useful to eliminate logging information.
969
+	offset := memoryMapSentinelOffset(s.Text())
970
+
967 971
 	var attrs []string
968 972
 	var r *strings.Replacer
969 973
 	const delimiter = "="
970 974
 	for s.Scan() {
971
-		line := strings.TrimSpace(s.Text())
972
-		if line == "" {
975
+		line := s.Text()
976
+		if len(line) > offset {
977
+			line = line[offset:]
978
+		}
979
+		if line = strings.TrimSpace(line); line == "" {
973 980
 			continue
974 981
 		}
975 982
 
@@ -1005,10 +1012,10 @@ func parseProcMapsFromScanner(s *bufio.Scanner) ([]*Mapping, error) {
1005 1012
 // /proc/self/maps, and overrides the mappings in the current profile.
1006 1013
 // It renumbers the samples and locations in the profile correspondingly.
1007 1014
 func (p *Profile) ParseMemoryMap(rd io.Reader) error {
1008
-	return p.parseMemoryMapFromScanner(bufio.NewScanner(rd))
1015
+	return p.ParseMemoryMapFromScanner(bufio.NewScanner(rd))
1009 1016
 }
1010 1017
 
1011
-func (p *Profile) parseMemoryMapFromScanner(s *bufio.Scanner) error {
1018
+func (p *Profile) ParseMemoryMapFromScanner(s *bufio.Scanner) error {
1012 1019
 	mapping, err := parseProcMapsFromScanner(s)
1013 1020
 	if err != nil {
1014 1021
 		return err
@@ -1054,25 +1061,32 @@ func parseMappingEntry(l string) (*Mapping, error) {
1054 1061
 	return mapping, nil
1055 1062
 }
1056 1063
 
1057
-type sectionType int
1058
-
1059
-const (
1060
-	unrecognizedSection sectionType = iota
1061
-	memoryMapSection
1062
-)
1063
-
1064
-var memoryMapTriggers = []string{
1064
+var memoryMapSentinels = []string{
1065 1065
 	"--- Memory map: ---",
1066 1066
 	"MAPPED_LIBRARIES:",
1067 1067
 }
1068 1068
 
1069
-func sectionTrigger(line string) sectionType {
1070
-	for _, trigger := range memoryMapTriggers {
1071
-		if strings.Contains(line, trigger) {
1072
-			return memoryMapSection
1069
+// isMemoryMapSentinel returns true if the string contains one of the
1070
+// known sentinels for memory map information.
1071
+func isMemoryMapSentinel(line string) bool {
1072
+	for _, s := range memoryMapSentinels {
1073
+		if strings.Contains(line, s) {
1074
+			return true
1075
+		}
1076
+	}
1077
+	return false
1078
+}
1079
+
1080
+// memoryMapSentinelOffset returns the index of a known memory map
1081
+// sentinel in the string. If the string does not contain a sentinel,
1082
+// it returns 0.
1083
+func memoryMapSentinelOffset(line string) int {
1084
+	for _, s := range memoryMapSentinels {
1085
+		if i := strings.Index(line, s); i != -1 {
1086
+			return i
1073 1087
 		}
1074 1088
 	}
1075
-	return unrecognizedSection
1089
+	return 0
1076 1090
 }
1077 1091
 
1078 1092
 func (p *Profile) addLegacyFrameInfo() {