📄 database.h
字号:
* @param size of region
*/
void deallocate(offs_t pos, size_t size);
/**
* Checks whther allocated size is greater than size of databae file and recreate
* memory mapping object with larger size n the last case
* @param size allocated size
*/
void extend(offs_t size);
/**
* Clone memory allocation bitmap for region [pos, pos+size)
* @param pos start of region
* @param size size of region
*/
void cloneBitmap(offs_t pos, size_t size);
/**
* Allocate object identifier(s)
* @param number of allocated object indentifiers
* @return object idenitifer (in case if n greater than 1, all n subsequent OIDs are
* allocated and first one is returned
*/
oid_t allocateId(int n = 1);
/**
* Free object identifier(s)
* @param oid deallocated object identifer (or first of n deallocated subsequent identifiers
* if n greater than 1)
* @param number of allocated object indentifiers
*/
void freeId(oid_t oid, int n = 1);
/**
* Update record in in all active cursors if it this record is checnged in the database
* @param oid object indentifier of checnged record
* @param removed true if record was removed
*/
void updateCursors(oid_t oid, bool removed = false);
/**
* Perform database recovery after fault
*/
void recovery();
/**
* Check if program works with correct version of memory mapped object (if memory mapped
* object is reallocated by some client, its version number is incremented, so
* all other client will be able to notice it and also reallocate their memory
* mapping objects.
* @return true if memory mapping object was successfully reallocated or no reallocation
* is needed at all
*/
bool checkVersion();
/**
* Allocate internal object
* @param market internal object tag
* @return oid of allocated object
*/
oid_t allocateObject(dbInternalObject marker)
{
oid_t oid = allocateId();
currIndex[oid] = allocate(internalObjectSize[marker]) + marker;
return oid;
}
/**
* Allocate record
* @param tableId object identifier of the table
* @param size size of the created record
* as table descriptor in the database
*/
oid_t allocateRow(oid_t tableId, size_t size)
{
oid_t oid = allocateId();
allocateRow(tableId, oid, size);
return oid;
}
/**
* Allocate record with specified OID
* @param tableId object identifier of the table
* @param oid record OID
* @param size size of the created record
* as table descriptor in the database
*/
void allocateRow(oid_t tableId, oid_t oid, size_t size);
/**
* Delete row from the table
* @param tableId OID of record with table descriptor
* @param oid identifier of deleted record
*/
void freeRow(oid_t tableId, oid_t oid);
/**
* Free internal object
*/
void freeObject(oid_t oid);
/**
* Cleanup compiled query
*/
static void deleteCompiledQuery(dbExprNode* tree);
/**
* Start database transaction
* @param modify if it is update or read-only rtansaction
* @return true if version of memory mapping object is not obsolete and reallocation
* is not possible
*/
enum dbLockType
{
dbSharedLock,
dbExclusiveLock,
dbCommitLock
};
bool beginTransaction(dbLockType);
/**
* End transaction
*/
void endTransaction()
{
endTransaction(threadContext.get());
}
/**
* End transaction with specified thread context
* @param ctx thread context
*/
void endTransaction(dbDatabaseThreadContext* ctx);
/**
* Initialize database metatable (table containning information about all other tables
* included metatable itself). This method is invoked during database initialzation.
*/
void initializeMetaTable();
/**
* Load database scheme. This method loads table decriptors from database,
* compare them with application classes, do necessary reformatting and save
* update andnew table decriptor in database
* @param alter if true then schema can be altered, otherwise there are some
* other active clients working with this database so schema can not be altered
*/
bool loadScheme(bool alter);
/**
* This method is invoked by SubSQL to complete table descriptors initialization
* after loading of all table descriptoes from thr database
* @return true if intertable relation consuistency is rpeservedm false otherwise
*/
bool completeDescriptorsInitialization();
/**
* Reformat table according to new format
* @param tableId OID of changed tables
* @param nw table descriptor
*/
void reformatTable(oid_t tableId, dbTableDescriptor* desc);
/**
* Add new indices to the table.
* @param alter if true than indices can be added, otherwise there are some other active
* clients and adding new indices about which they will not know can lead to inconsistncy
* @param desc new table descriptor
* @return true if indices were succesfully added
*/
bool addIndices(bool alter, dbTableDescriptor* desc);
/**
* Add new table to the database
* @param desc - descriptor of new table
* @return oid of created table descriptor record
*/
oid_t addNewTable(dbTableDescriptor* desc);
/**
* Update database table descriptor
* @param desc application table descriptor
* @param tableId OID of recrods with database table descriptor
*/
void updateTableDescriptor(dbTableDescriptor* desc, oid_t tableId);
/**
* Insert inverse reference. When reference or array of reference which is part of relation is updated
* then reference to the updated record is inserted in inverse reference field of all
* new referenced records (which were not referenced by this field before update).
* @param fd descriptor of updated field (inverse reference should exist for this field)
* @param reverseId OID of updated record
* @param targetId OID of record referenced by this field
*/
void insertInverseReference(dbFieldDescriptor* fd,
oid_t reverseId, oid_t targetId);
/**
* Remove inverse references to the removed record
* @param desc descriptor of table from which record is removed
* @param oid OID of removed record
*/
void removeInverseReferences(dbTableDescriptor* desc, oid_t oid);
/**
* Remove inverse reference. When reference or array of reference which is part of relation is updated
* then reference to the updated record is removed from inverse reference field of all
* referenced records which are not reference any more from by this field.
* @param fd descriptor of updated field (inverse reference should exist for this field)
* @param reverseId OID of updated record
* @param targetId OID of record referenced by this field
*/
void removeInverseReference(dbFieldDescriptor* fd,
oid_t reverseId, oid_t targetId);
/**
* Delete table from the database
* @param desc table descriptor
*/
void deleteTable(dbTableDescriptor* desc);
/**
* Delete all table records
* @param desc table descriptor
*/
void dropTable(dbTableDescriptor* desc);
/**
* Create T-Tree index for the field
* @param fd field descriptor
*/
void createIndex(dbFieldDescriptor* fd);
/**
* Create hash table for the field
* @param fd field descriptor
*/
void createHashTable(dbFieldDescriptor* fd);
/**
* Drop T-Tree index for the field
* @param fd field descriptor
*/
void dropIndex(dbFieldDescriptor* fd);
/**
* Drop hash table for the field
* @param fd field descriptor
*/
void dropHashTable(dbFieldDescriptor* fd);
/**
* Link table to the database table list
* @param table table descriptor
* @param tableId OID of record containing database table descriptor
*/
void linkTable(dbTableDescriptor* table, oid_t tableId);
/**
* Unlink table from the database tables list
* @param table table descriptor
*/
void unlinkTable(dbTableDescriptor* table);
/**
* Check if location is reserved
* @param pos start position of the location
* @param size location size
* @return true id location was reserved
*/
bool wasReserved(offs_t pos, size_t size);
/**
* Mark location as reserved. This method is used by allocator to protect hole
* located in memory allocation bitmap, from been used by recursuve call of allocator (needed to clone
* bitmap pages).
* @param location [out] local structure describing location.
* @param pos start position of the location
* @param size location size
*/
void reserveLocation(dbLocation& location, offs_t pos, size_t size);
/**
* Remove location from list of reserved locations. It is done after location is marked
* as occupied in bitmap.
*/
void commitLocation();
/**
* Find table using symbol name
* @param name symbol table entry (returned by dbSymbolTable::add method)
* @return table descriptor or <code>NULL</code> if not found
*/
dbTableDescriptor* findTable(char const* name);
/**
* Find table by name. This method get symbol for specified name and call <code>findTable</code>
* method.
* @param name name of table
* @return table descriptor or <code>NULL</code> if not found
*/
dbTableDescriptor* findTableByName(char const* name);
/**
* Get list of tables attached to the database
* @return list of tables attached to the database
*/
dbTableDescriptor* getTables();
/**
* Mark database as been modified
*/
void setDirty();
};
#ifdef REPLICATION_SUPPORT
#include "sockio.h"
class FASTDB_DLL_ENTRY dbConnection
{
public:
socket_t* reqSock;
socket_t* respSock;
dbLocalEvent statusEvent;
dbLocalEvent readyEvent;
dbLocalEvent useEvent;
dbMutex writeCS;
int useCount;
int waitUseEventFlag;
int waitStatusEventFlag;
int status;
dbConnection()
{
readyEvent.open();
useEvent.open();
statusEvent.open();
useCount = 0;
waitUseEventFlag = 0;
waitStatusEventFlag = 0;
status = 0;
reqSock = respSock = NULL;
}
~dbConnection()
{
readyEvent.close();
useEvent.close();
statusEvent.close();
delete reqSock;
delete respSock;
}
};
class FASTDB_DLL_ENTRY dbReplicatedDatabase : public dbDatabase
{
friend class dbFile;
protected:
char** serverURL;
int nServers;
int id;
dbConnection* con;
enum NodeStatus {
ST_OFFLINE, // node is not available
ST_ONLINE, // node is available
ST_ACTIVE, // primary node is running, replicating changes
ST_STANDBY, // standby node receives changes from primary node
ST_RECOVERED // node is recovered after the fault
};
dbLocalEvent startEvent;
dbMutex startCS;
fd_set inputSD;
int nInputSD;
int activeNodeId;
dbMutex sockCS;
socket_t* acceptSock;
dbThread readerThread;
static void thread_proc dbReplicatedDatabase::startReader(void* arg);
void reader();
public:
void deleteConnection(int nodeId);
void lockConnection(int nodeId);
void unlockConnection(int nodeId);
void changeActiveNode();
void addConnection(int nodeId, socket_t* s);
bool writeReq(int nodeId, ReplicationRequest const& hdr,
void* body = NULL, size_t bodySize = 0);
bool writeResp(int nodeId, ReplicationRequest const& hdr);
bool open(char const* databaseName, char const* fileName,
int id, char* servers[], int nServers);
virtual void close();
static int dbPollInterval;
static int dbWaitReadyTimeout;
static int dbWaitStatusTimeout;
static int dbRecoveryConnectionAttempts;
static int dbStartupConnectionAttempts;
dbReplicatedDatabase(dbAccessType type = dbAllAccess,
size_t dbInitSize = dbDefaultInitDatabaseSize,
size_t dbExtensionQuantum = dbDefaultExtensionQuantum,
size_t dbInitIndexSize = dbDefaultInitIndexSize,
int nThreads = 1)
: dbDatabase(type, dbInitSize, dbExtensionQuantum, dbInitIndexSize, nThreads)
{}
}
;
#endif
template<class T>
dbReference<T> insert(T const& record)
{
dbReference<T> ref;
T::dbDescriptor.getDatabase()->insertRecord(&T::dbDescriptor, &ref, &record);
return ref;
}
#ifdef NO_MEMBER_TEMPLATES
template<class T>
dbReference<T> insert(dbDatabase& db, T const& record)
{
dbReference<T> ref;
db.insertRecord(db.lookupTable(&T::dbDescriptor), &ref, &record);
return ref;
}
#endif
/**
* Search contrext used to pass information about search parameters to T-Tree and Hash table index implementations
*/
class dbSearchContext
{
public:
dbDatabase* db;
dbExprNode* condition;
dbAnyCursor* cursor;
char* firstKey;
int firstKeyInclusion;
char* lastKey;
int lastKeyInclusion;
int type;
int sizeofType;
dbUDTComparator comparator;
int offs;
int probes;
};
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -