From bf543df20ccd9e2c422751908cabf073bc7f5d4b Mon Sep 17 00:00:00 2001 From: Harald Weppner Date: Mon, 17 Mar 2014 23:53:00 -0700 Subject: [PATCH] Enable profiling / leak detection in FreeBSD * Assumes procfs is mounted at /proc, cf. --- bin/pprof | 22 ++++++++++++++++++++-- src/prof.c | 8 +++++++- 2 files changed, 27 insertions(+), 3 deletions(-) diff --git a/bin/pprof b/bin/pprof index 727eb437..08c9ea31 100755 --- a/bin/pprof +++ b/bin/pprof @@ -4197,8 +4197,12 @@ sub FindLibrary { # For libc libraries, the copy in /usr/lib/debug contains debugging symbols sub DebuggingLibrary { my $file = shift; - if ($file =~ m|^/| && -f "/usr/lib/debug$file") { - return "/usr/lib/debug$file"; + if ($file =~ m|^/|) { + if (-f "/usr/lib/debug$file") { + return "/usr/lib/debug$file"; + } elsif (-f "/usr/lib/debug$file.debug") { + return "/usr/lib/debug$file.debug"; + } } return undef; } @@ -4360,6 +4364,19 @@ sub ParseLibraries { $finish = HexExtend($2); $offset = $zero_offset; $lib = $3; + } + # FreeBSD 10.0 virtual memory map /proc/curproc/map as defined in + # function procfs_doprocmap (sys/fs/procfs/procfs_map.c) + # + # Example: + # 0x800600000 0x80061a000 26 0 0xfffff800035a0000 r-x 75 33 0x1004 COW NC vnode /libexec/ld-elf.s + # o.1 NCH -1 + elsif ($l =~ /^(0x$h)\s(0x$h)\s\d+\s\d+\s0x$h\sr-x\s\d+\s\d+\s0x\d+\s(COW|NCO)\s(NC|NNC)\svnode\s(\S+\.so(\.\d+)*)/) { + $start = HexExtend($1); + $finish = HexExtend($2); + $offset = $zero_offset; + $lib = FindLibrary($5); + } else { next; } @@ -4382,6 +4399,7 @@ sub ParseLibraries { } } + if($main::opt_debug) { printf STDERR "$start:$finish ($offset) $lib\n"; } push(@{$result}, [$lib, $start, $finish, $offset]); } diff --git a/src/prof.c b/src/prof.c index 1d8ccbd6..ede89a7a 100644 --- a/src/prof.c +++ b/src/prof.c @@ -11,6 +11,12 @@ #include #endif +#ifdef __FreeBSD__ +#define PROCESS_VMEM_MAP "/proc/curproc/map" +#else +#define PROCESS_VMEM_MAP "/proc/%d/maps" +#endif + /******************************************************************************/ /* Data. */ @@ -936,7 +942,7 @@ prof_dump_maps(bool propagate_err) cassert(config_prof); - malloc_snprintf(filename, sizeof(filename), "/proc/%d/maps", + malloc_snprintf(filename, sizeof(filename), PROCESS_VMEM_MAP, (int)getpid()); mfd = open(filename, O_RDONLY); if (mfd != -1) {