#include "crc32c.h"
#include "assert.h"
+#include "common/Spinlock.h"
+
extern atomic_t buffer_total_alloc;
+extern Spinlock buffer_lock;
+
+//#define BUFFER_DEBUG
+
+#ifdef BUFFER_DEBUG
+# define bdout { buffer_lock.lock(); cout
+# define bendl std::endl; buffer_lock.unlock(); }
+#else
+# define bdout if (0) { cout
+# define bendl std::endl; }
+#endif
class buffer {
/*
else
data = 0;
inc_total_alloc(len);
+ bdout << "raw_char alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
raw_char(unsigned l, char *b) : raw(b, l) {
inc_total_alloc(len);
+ bdout << "raw_char alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
~raw_char() {
delete[] data;
dec_total_alloc(len);
+ bdout << "raw_char free " << (void *)data << " " << buffer_total_alloc.test() << bendl;
}
raw* clone_empty() {
return new raw_char(len);
else
data = 0;
inc_total_alloc(len);
+ bdout << "raw_malloc alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
raw_malloc(unsigned l, char *b) : raw(b, l) {
inc_total_alloc(len);
+ bdout << "raw_malloc alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
~raw_malloc() {
free(data);
dec_total_alloc(len);
+ bdout << "raw_malloc free " << (void *)data << " " << buffer_total_alloc.test() << bendl;
}
raw* clone_empty() {
return new raw_malloc(len);
if (!data)
throw new bad_alloc;
inc_total_alloc(len);
+ bdout << "raw_mmap alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
~raw_mmap_pages() {
::munmap(data, len);
dec_total_alloc(len);
+ bdout << "raw_mmap free " << (void *)data << " " << buffer_total_alloc.test() << bendl;
}
raw* clone_empty() {
return new raw_mmap_pages(len);
if (!data)
throw new bad_alloc;
inc_total_alloc(len);
+ bdout << "raw_posix_aligned alloc " << (void *)data << " " << l << " " << buffer_total_alloc.test() << bendl;
}
~raw_posix_aligned() {
::free((void*)data);
dec_total_alloc(len);
+ bdout << "raw_posix_aligned free " << (void *)data << " " << buffer_total_alloc.test() << bendl;
}
raw* clone_empty() {
return new raw_posix_aligned(len);
use strict;
my %buffers;
-my %bufferlists;
-my %ref;
-my %mal;
+
my $l = 1;
while (<>) {
- #print "$l: $_";
-
- # cinode:auth_pin on inode [1000000002625 /gnu/blah_client_created. 0x89b7700] count now 1 + 0
-
- if (/^buffer\.cons /) {
- my ($x) = /(0x\S+)/;
- $buffers{$x} = 1;
- }
- if (/^buffer\.des /) {
- my ($x) = /(0x\S+)/;
- die "des without cons at $l: $_" unless $buffers{$x};
- delete $buffers{$x};
- die "des with ref>0 at $l: $_" unless $ref{$x} == 0;
- delete $ref{$x};
- }
-
- if (/^bufferlist\.cons /) {
- my ($x) = /(0x\S+)/;
- $bufferlists{$x} = 1;
- }
- if (/^bufferlist\.des /) {
- my ($x) = /(0x\S+)/;
- warn "des without cons at $l: $_" unless $bufferlists{$x};
- delete $bufferlists{$x};
- }
-
-
- if (/^buffer\.malloc /) {
- my ($x) = /(0x\S+)/;
- $mal{$x} = 1;
- }
- if (/^buffer\.free /) {
- my ($x) = /(0x\S+)/;
- die "free with malloc at $l: $_" unless $mal{$x};
- delete $mal{$x};
- }
-
- if (/^buffer\.get /) {
- my ($x) = /(0x\S+)/;
- $ref{$x}++;
- }
- if (/^buffer\.get /) {
- my ($x) = /(0x\S+)/;
- $ref{$x}--;
- }
-
-$l++;
-}
-
-for my $x (keys %bufferlists) {
- print "leaked bufferlist $x\n";
-}
-
-for my $x (keys %buffers) {
- print "leaked buffer $x ref $ref{$x}\n";
+ #print "$l: $_";
+
+ if (/^raw_(\w+) alloc (\S+)/) {
+ #print "alloc $2\n";
+ $buffers{$2} = "$l: $_";
+ }
+ if (/^raw_(\w+) free (\S+)/) {
+ #print "free $2\n";
+ print "free without alloc at $l: $_" unless $buffers{$2};
+ delete $buffers{$2};
+ }
+ $l++;
}
-for my $x (keys %mal) {
- print "leaked buffer dataptr $x ref $ref{$x}\n";
+for my $x (sort {$buffers{$a} <=> $buffers{$b}} keys %buffers) {
+ print "leaked $buffers{$x}";
}