Remote whitespace at the ends of lines. Remove blank lines from the ends of files. Change modes on source files so that they are not executable. Signed-off-by: Dan Cross <cross@gajendra.net>
271 lines
4.1 KiB
C
271 lines
4.1 KiB
C
#include "stdinc.h"
|
|
#include <bio.h>
|
|
#include "dat.h"
|
|
#include "fns.h"
|
|
#include "error.h"
|
|
|
|
int num = 100;
|
|
int length = 20*1024;
|
|
int block= 1024;
|
|
int bush = 4;
|
|
int iter = 100;
|
|
Biobuf *bout;
|
|
int maxdepth;
|
|
|
|
Source *mkroot(Cache*);
|
|
void new(Source*, int trace, int);
|
|
int delete(Source*);
|
|
int count(Source *s, int);
|
|
void stats(Source *s);
|
|
void dump(Source *s, int ident, ulong entry);
|
|
static void bench(Source *r);
|
|
|
|
void
|
|
main(int argc, char *argv[])
|
|
{
|
|
int i;
|
|
Fs *fs;
|
|
int csize = 1000;
|
|
ulong t;
|
|
Source *r;
|
|
|
|
ARGBEGIN{
|
|
case 'i':
|
|
iter = atoi(ARGF());
|
|
break;
|
|
case 'n':
|
|
num = atoi(ARGF());
|
|
break;
|
|
case 'l':
|
|
length = atoi(ARGF());
|
|
break;
|
|
case 'b':
|
|
block = atoi(ARGF());
|
|
break;
|
|
case 'u':
|
|
bush = atoi(ARGF());
|
|
break;
|
|
case 'c':
|
|
csize = atoi(ARGF());
|
|
break;
|
|
}ARGEND;
|
|
|
|
vtAttach();
|
|
|
|
bout = vtMemAllocZ(sizeof(Biobuf));
|
|
Binit(bout, 1, OWRITE);
|
|
|
|
fmtinstall('V', vtScoreFmt);
|
|
fmtinstall('R', vtErrFmt);
|
|
|
|
fs = fsOpen(argv[0], nil, csize, OReadWrite);
|
|
if(fs == nil)
|
|
sysfatal("could not open fs: %r");
|
|
|
|
t = time(0);
|
|
|
|
srand(0);
|
|
|
|
r = fs->source;
|
|
dump(r, 0, 0);
|
|
|
|
fprint(2, "count = %d\n", count(r, 1));
|
|
for(i=0; i<num; i++)
|
|
new(r, 0, 0);
|
|
|
|
for(i=0; i<iter; i++){
|
|
if(i % 10000 == 0)
|
|
stats(r);
|
|
new(r, 0, 0);
|
|
delete(r);
|
|
}
|
|
|
|
// dump(r, 0, 0);
|
|
|
|
fprint(2, "count = %d\n", count(r, 1));
|
|
// cacheCheck(c);
|
|
|
|
fprint(2, "deleting\n");
|
|
for(i=0; i<num; i++)
|
|
delete(r);
|
|
// dump(r, 0, 0);
|
|
|
|
fprint(2, "count = %d\n", count(r, 1));
|
|
fprint(2, "total time = %ld\n", time(0)-t);
|
|
|
|
fsClose(fs);
|
|
vtDetach();
|
|
exits(0);
|
|
}
|
|
|
|
static void
|
|
bench(Source *r)
|
|
{
|
|
vlong t;
|
|
Entry e;
|
|
int i;
|
|
|
|
t = nsec();
|
|
|
|
for(i=0; i<1000000; i++)
|
|
sourceGetEntry(r, &e);
|
|
|
|
fprint(2, "%f\n", 1e-9*(nsec() - t));
|
|
}
|
|
|
|
void
|
|
new(Source *s, int trace, int depth)
|
|
{
|
|
int i, n;
|
|
Source *ss;
|
|
Entry e;
|
|
|
|
if(depth > maxdepth)
|
|
maxdepth = depth;
|
|
|
|
Bflush(bout);
|
|
|
|
n = sourceGetDirSize(s);
|
|
for(i=0; i<n; i++){
|
|
ss = sourceOpen(s, nrand(n), OReadWrite);
|
|
if(ss == nil || !sourceGetEntry(ss, &e))
|
|
continue;
|
|
if((e.flags & VtEntryDir) && frand() < 1./bush){
|
|
if(trace){
|
|
int j;
|
|
for(j=0; j<trace; j++)
|
|
Bprint(bout, " ");
|
|
Bprint(bout, "decend %d\n", i);
|
|
}
|
|
new(ss, trace?trace+1:0, depth+1);
|
|
sourceClose(ss);
|
|
return;
|
|
}
|
|
sourceClose(ss);
|
|
}
|
|
ss = sourceCreate(s, s->dsize, 1+frand()>.5, 0);
|
|
if(ss == nil){
|
|
Bprint(bout, "could not create directory: %R\n");
|
|
return;
|
|
}
|
|
if(trace){
|
|
int j;
|
|
for(j=1; j<trace; j++)
|
|
Bprint(bout, " ");
|
|
Bprint(bout, "create %d\n", ss->offset);
|
|
}
|
|
sourceClose(ss);
|
|
}
|
|
|
|
int
|
|
delete(Source *s)
|
|
{
|
|
int i, n;
|
|
Source *ss;
|
|
|
|
n = sourceGetDirSize(s);
|
|
/* check if empty */
|
|
for(i=0; i<n; i++){
|
|
ss = sourceOpen(s, i, OReadWrite);
|
|
if(ss != nil){
|
|
sourceClose(ss);
|
|
break;
|
|
}
|
|
}
|
|
if(i == n)
|
|
return 0;
|
|
|
|
for(;;){
|
|
ss = sourceOpen(s, nrand(n), OReadWrite);
|
|
if(ss == nil)
|
|
continue;
|
|
if(s->dir && delete(ss)){
|
|
sourceClose(ss);
|
|
return 1;
|
|
}
|
|
if(1)
|
|
break;
|
|
sourceClose(ss);
|
|
}
|
|
|
|
|
|
sourceRemove(ss);
|
|
return 1;
|
|
}
|
|
|
|
void
|
|
dump(Source *s, int ident, ulong entry)
|
|
{
|
|
ulong i, n;
|
|
Source *ss;
|
|
Entry e;
|
|
|
|
for(i=0; i<ident; i++)
|
|
Bprint(bout, " ");
|
|
|
|
if(!sourceGetEntry(s, &e)){
|
|
fprint(2, "sourceGetEntry failed: %r\n");
|
|
return;
|
|
}
|
|
|
|
Bprint(bout, "%4lud: gen %4ud depth %d tag=%x score=%V",
|
|
entry, e.gen, e.depth, e.tag, e.score);
|
|
if(!s->dir){
|
|
Bprint(bout, " data size: %llud\n", e.size);
|
|
return;
|
|
}
|
|
n = sourceGetDirSize(s);
|
|
Bprint(bout, " dir size: %lud\n", n);
|
|
for(i=0; i<n; i++){
|
|
ss = sourceOpen(s, i, 1);
|
|
if(ss == nil)
|
|
continue;
|
|
dump(ss, ident+1, i);
|
|
sourceClose(ss);
|
|
}
|
|
return;
|
|
}
|
|
|
|
int
|
|
count(Source *s, int rec)
|
|
{
|
|
ulong i, n;
|
|
int c;
|
|
Source *ss;
|
|
|
|
n = sourceGetDirSize(s);
|
|
c = 0;
|
|
for(i=0; i<n; i++){
|
|
ss = sourceOpen(s, i, OReadOnly);
|
|
if(ss == nil)
|
|
continue;
|
|
if(rec)
|
|
c += count(ss, rec);
|
|
c++;
|
|
sourceClose(ss);
|
|
}
|
|
return c;
|
|
}
|
|
|
|
void
|
|
stats(Source *s)
|
|
{
|
|
int n, i, c, cc, max;
|
|
Source *ss;
|
|
|
|
cc = 0;
|
|
max = 0;
|
|
n = sourceGetDirSize(s);
|
|
for(i=0; i<n; i++){
|
|
ss = sourceOpen(s, i, 1);
|
|
if(ss == nil)
|
|
continue;
|
|
cc++;
|
|
c = count(ss, 1);
|
|
if(c > max)
|
|
max = c;
|
|
sourceClose(ss);
|
|
}
|
|
fprint(2, "count = %d top = %d depth=%d maxcount %d\n", cc, n, maxdepth, max);
|
|
}
|