0
0
mirror of https://github.com/mongodb/mongo.git synced 2024-12-01 09:32:32 +01:00
mongodb/db/namespace.h
2007-11-10 16:46:30 -05:00

129 lines
2.7 KiB
C++

// namespace.h
#pragma once
#include "../util/hashtab.h"
#include "../util/mmap.h"
class Cursor;
class Namespace {
public:
Namespace(const char *ns) {
*this = ns;
}
Namespace& operator=(const char *ns) {
memset(buf, 0, 128); /* this is just to keep stuff clean in the files for easy dumping and reading */
strcpy_s(buf, 128, ns); return *this;
}
bool operator==(const Namespace& r) { return strcmp(buf, r.buf) == 0; }
int hash() const {
unsigned x = 0;
const char *p = buf;
while( *p ) {
x = x * 131 + *p;
p++;
}
return (x & 0x7fffffff) | 0x8000000; // must be > 0
}
char buf[128];
};
const int Buckets = 19;
const int MaxBucket = 18;
const int MaxIndexes = 10;
class IndexDetails {
public:
DiskLoc head; /* btree head */
DiskLoc info; /* index info object. { name:, ns:, key: } */
};
extern int bucketSizes[];
class NamespaceDetails {
public:
NamespaceDetails() {
datasize = nrecords = 0;
lastExtentSize = 0;
nIndexes = 0;
memset(reserved, 0, sizeof(reserved));
}
DiskLoc firstExtent;
DiskLoc deletedList[Buckets];
long long datasize;
long long nrecords;
int lastExtentSize;
int nIndexes;
IndexDetails indexes[MaxIndexes];
char reserved[256-16-4-4-8*MaxIndexes];
//returns offset in indexes[]
int findIndexByName(const char *name) {
for( int i = 0; i < nIndexes; i++ ) {
if( strcmp(indexes[i].info.obj().getStringField("name"),name) == 0 )
return i;
}
return -1;
}
static int bucket(int n) {
for( int i = 0; i < Buckets; i++ )
if( bucketSizes[i] > n )
return i;
return Buckets-1;
}
DiskLoc alloc(int lenToAlloc, DiskLoc& extentLoc);
void addDeletedRec(DeletedRecord *d, DiskLoc dloc);
private:
DiskLoc _alloc(int len);
};
class NamespaceIndex {
friend class NamespaceCursor;
public:
NamespaceIndex() { }
void init() {
const int LEN = 16 * 1024 * 1024;
void *p = f.map("/data/db/namespace.idx", LEN);
if( p == 0 ) {
cout << "couldn't open /data/db/namespace.idx" << endl;
exit(-3);
}
ht = new HashTable<Namespace,NamespaceDetails>(p, LEN, "namespace index");
}
void add(const char *ns, DiskLoc& loc) {
Namespace n(ns);
NamespaceDetails details;
details.firstExtent = loc;
ht->put(n, details);
}
NamespaceDetails* details(const char *ns) {
Namespace n(ns);
return ht->get(n);
}
bool find(const char *ns, DiskLoc& loc) {
NamespaceDetails *l = details(ns);
if( l ) {
loc = l->firstExtent;
return true;
}
return false;
}
private:
MemoryMappedFile f;
HashTable<Namespace,NamespaceDetails> *ht;
};
extern NamespaceIndex namespaceIndex;
auto_ptr<Cursor> makeNamespaceCursor();