more refactoring; no more globals in transactionTable.c
This commit is contained in:
parent
dbe3ecf0d0
commit
4565aff9de
16 changed files with 213 additions and 195 deletions
|
@ -112,7 +112,7 @@ int main(int argc, char ** argv) {
|
||||||
} */
|
} */
|
||||||
}
|
}
|
||||||
if(net) {
|
if(net) {
|
||||||
last_lsn = stasis_transaction_table[xid%MAX_TRANSACTIONS].prevLSN;
|
last_lsn = stasis_transaction_table_get(stasis_runtime_transaction_table(), xid)->prevLSN;
|
||||||
}
|
}
|
||||||
Tcommit(xid);
|
Tcommit(xid);
|
||||||
}
|
}
|
||||||
|
|
|
@ -157,7 +157,7 @@ void * writeback_unit_of_work(void * ap) {
|
||||||
|
|
||||||
stasis_log_reordering_handle_t * rh
|
stasis_log_reordering_handle_t * rh
|
||||||
= stasis_log_reordering_handle_open(
|
= stasis_log_reordering_handle_open(
|
||||||
&stasis_transaction_table[ua->xid%MAX_TRANSACTIONS],
|
stasis_transaction_table_get(stasis_runtime_transaction_table(), ua->xid),
|
||||||
stasis_log(),
|
stasis_log(),
|
||||||
(0.9*stasis_log_file_write_buffer_size)/ua->divisor,
|
(0.9*stasis_log_file_write_buffer_size)/ua->divisor,
|
||||||
//512*1024/ua->divisor, // 0.5 mb in log tail at once
|
//512*1024/ua->divisor, // 0.5 mb in log tail at once
|
||||||
|
@ -199,7 +199,7 @@ void * bg_unit_of_work(void * ap) {
|
||||||
bulk_worker_args * a = ua->a;
|
bulk_worker_args * a = ua->a;
|
||||||
|
|
||||||
stasis_log_reordering_handle_t * rh
|
stasis_log_reordering_handle_t * rh
|
||||||
= stasis_log_reordering_handle_open(&stasis_transaction_table[ua->xid%MAX_TRANSACTIONS],
|
= stasis_log_reordering_handle_open(stasis_transaction_table_get(stasis_runtime_transaction_table(), ua->xid),
|
||||||
stasis_log(),
|
stasis_log(),
|
||||||
(stasis_log_file_write_buffer_size * 0.25)/ua->divisor,
|
(stasis_log_file_write_buffer_size * 0.25)/ua->divisor,
|
||||||
//512*1024/ua->divisor, // 0.5 mb in log tail at once
|
//512*1024/ua->divisor, // 0.5 mb in log tail at once
|
||||||
|
|
|
@ -52,7 +52,7 @@ terms specified in this license.
|
||||||
#include <stasis/logger/inMemoryLog.h>
|
#include <stasis/logger/inMemoryLog.h>
|
||||||
#include <stasis/page.h>
|
#include <stasis/page.h>
|
||||||
|
|
||||||
static lsn_t stasis_log_write_common(stasis_log_t* log, TransactionLog * l, int type) {
|
static lsn_t stasis_log_write_common(stasis_log_t* log, stasis_transaction_table_entry_t * l, int type) {
|
||||||
LogEntry * e = allocCommonLogEntry(l->prevLSN, l->xid, type);
|
LogEntry * e = allocCommonLogEntry(l->prevLSN, l->xid, type);
|
||||||
lsn_t ret;
|
lsn_t ret;
|
||||||
|
|
||||||
|
@ -73,7 +73,7 @@ static lsn_t stasis_log_write_common(stasis_log_t* log, TransactionLog * l, int
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static lsn_t stasis_log_write_prepare(stasis_log_t* log, TransactionLog * l) {
|
static lsn_t stasis_log_write_prepare(stasis_log_t* log, stasis_transaction_table_entry_t * l) {
|
||||||
LogEntry * e = allocPrepareLogEntry(l->prevLSN, l->xid, l->recLSN);
|
LogEntry * e = allocPrepareLogEntry(l->prevLSN, l->xid, l->recLSN);
|
||||||
lsn_t ret;
|
lsn_t ret;
|
||||||
|
|
||||||
|
@ -96,7 +96,7 @@ static lsn_t stasis_log_write_prepare(stasis_log_t* log, TransactionLog * l) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
LogEntry * stasis_log_write_update(stasis_log_t* log, TransactionLog * l,
|
LogEntry * stasis_log_write_update(stasis_log_t* log, stasis_transaction_table_entry_t * l,
|
||||||
pageid_t page, unsigned int op,
|
pageid_t page, unsigned int op,
|
||||||
const byte * arg, size_t arg_size) {
|
const byte * arg, size_t arg_size) {
|
||||||
|
|
||||||
|
@ -113,12 +113,12 @@ LogEntry * stasis_log_write_update(stasis_log_t* log, TransactionLog * l,
|
||||||
return e;
|
return e;
|
||||||
}
|
}
|
||||||
|
|
||||||
LogEntry * stasis_log_begin_nta(stasis_log_t* log, TransactionLog * l, unsigned int op,
|
LogEntry * stasis_log_begin_nta(stasis_log_t* log, stasis_transaction_table_entry_t * l, unsigned int op,
|
||||||
const byte * arg, size_t arg_size) {
|
const byte * arg, size_t arg_size) {
|
||||||
LogEntry * e = allocUpdateLogEntry(l->prevLSN, l->xid, op, INVALID_PAGE, arg, arg_size);
|
LogEntry * e = allocUpdateLogEntry(l->prevLSN, l->xid, op, INVALID_PAGE, arg, arg_size);
|
||||||
return e;
|
return e;
|
||||||
}
|
}
|
||||||
lsn_t stasis_log_end_nta(stasis_log_t* log, TransactionLog * l, LogEntry * e) {
|
lsn_t stasis_log_end_nta(stasis_log_t* log, stasis_transaction_table_entry_t * l, LogEntry * e) {
|
||||||
log->write_entry(log, e);
|
log->write_entry(log, e);
|
||||||
pthread_mutex_lock(&l->mut);
|
pthread_mutex_lock(&l->mut);
|
||||||
if(l->prevLSN == INVALID_LSN) { l->recLSN = e->LSN; }
|
if(l->prevLSN == INVALID_LSN) { l->recLSN = e->LSN; }
|
||||||
|
@ -149,7 +149,7 @@ lsn_t stasis_log_write_dummy_clr(stasis_log_t* log, int xid, lsn_t prevLSN) {
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void stasis_log_begin_transaction(stasis_log_t* log, int xid, TransactionLog* tl) {
|
void stasis_log_begin_transaction(stasis_log_t* log, int xid, stasis_transaction_table_entry_t* tl) {
|
||||||
tl->xid = xid;
|
tl->xid = xid;
|
||||||
|
|
||||||
DEBUG("Log Begin %d\n", xid);
|
DEBUG("Log Begin %d\n", xid);
|
||||||
|
@ -157,20 +157,20 @@ void stasis_log_begin_transaction(stasis_log_t* log, int xid, TransactionLog* tl
|
||||||
tl->recLSN = INVALID_LSN;
|
tl->recLSN = INVALID_LSN;
|
||||||
}
|
}
|
||||||
|
|
||||||
lsn_t stasis_log_abort_transaction(stasis_log_t* log, TransactionLog * l) {
|
lsn_t stasis_log_abort_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l) {
|
||||||
return stasis_log_write_common(log, l, XABORT);
|
return stasis_log_write_common(log, l, XABORT);
|
||||||
}
|
}
|
||||||
lsn_t stasis_log_end_aborted_transaction(stasis_log_t* log, TransactionLog * l) {
|
lsn_t stasis_log_end_aborted_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l) {
|
||||||
return stasis_log_write_common(log, l, XEND);
|
return stasis_log_write_common(log, l, XEND);
|
||||||
}
|
}
|
||||||
lsn_t stasis_log_prepare_transaction(stasis_log_t* log, TransactionLog * l) {
|
lsn_t stasis_log_prepare_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l) {
|
||||||
lsn_t lsn = stasis_log_write_prepare(log, l);
|
lsn_t lsn = stasis_log_write_prepare(log, l);
|
||||||
stasis_log_force(log, lsn, LOG_FORCE_COMMIT);
|
stasis_log_force(log, lsn, LOG_FORCE_COMMIT);
|
||||||
return lsn;
|
return lsn;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
lsn_t stasis_log_commit_transaction(stasis_log_t* log, TransactionLog * l, int force) {
|
lsn_t stasis_log_commit_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l, int force) {
|
||||||
lsn_t lsn = stasis_log_write_common(log, l, XCOMMIT);
|
lsn_t lsn = stasis_log_write_common(log, l, XCOMMIT);
|
||||||
if(force) {
|
if(force) {
|
||||||
stasis_log_force(log, lsn, LOG_FORCE_COMMIT);
|
stasis_log_force(log, lsn, LOG_FORCE_COMMIT);
|
||||||
|
|
|
@ -75,7 +75,7 @@ void stasis_log_reordering_handle_close(stasis_log_reordering_handle_t * h) {
|
||||||
free(h);
|
free(h);
|
||||||
}
|
}
|
||||||
stasis_log_reordering_handle_t *
|
stasis_log_reordering_handle_t *
|
||||||
stasis_log_reordering_handle_open(TransactionLog * l,
|
stasis_log_reordering_handle_open(stasis_transaction_table_entry_t * l,
|
||||||
stasis_log_t* log,
|
stasis_log_t* log,
|
||||||
size_t chunk_len,
|
size_t chunk_len,
|
||||||
size_t max_len,
|
size_t max_len,
|
||||||
|
|
|
@ -8,6 +8,9 @@
|
||||||
#include <pbl/pbl.h>
|
#include <pbl/pbl.h>
|
||||||
|
|
||||||
#include <stasis/recovery.h>
|
#include <stasis/recovery.h>
|
||||||
|
|
||||||
|
#include <stasis/transactionTable.h>
|
||||||
|
|
||||||
#include <stasis/bufferManager.h>
|
#include <stasis/bufferManager.h>
|
||||||
#include <stasis/lockManager.h>
|
#include <stasis/lockManager.h>
|
||||||
|
|
||||||
|
@ -45,7 +48,7 @@ static pthread_mutex_t rollback_mutex = PTHREAD_MUTEX_INITIALIZER;
|
||||||
no longer reads the pages in, there's no longer any reason to build
|
no longer reads the pages in, there's no longer any reason to build
|
||||||
the list of dirty pages.
|
the list of dirty pages.
|
||||||
*/
|
*/
|
||||||
static void stasis_recovery_analysis(stasis_log_t* log) {
|
static void stasis_recovery_analysis(stasis_log_t* log, stasis_transaction_table_t * tbl) {
|
||||||
|
|
||||||
DEBUG("Recovery: Analysis\n");
|
DEBUG("Recovery: Analysis\n");
|
||||||
|
|
||||||
|
@ -111,7 +114,7 @@ static void stasis_recovery_analysis(stasis_log_t* log) {
|
||||||
lsn_t* free_lsn = pblHtLookup(transactionLSN, &(e->xid), sizeof(int));
|
lsn_t* free_lsn = pblHtLookup(transactionLSN, &(e->xid), sizeof(int));
|
||||||
pblHtRemove(transactionLSN, &(e->xid), sizeof(int));
|
pblHtRemove(transactionLSN, &(e->xid), sizeof(int));
|
||||||
free(free_lsn);
|
free(free_lsn);
|
||||||
stasis_transaction_table_forget(e->xid);
|
stasis_transaction_table_forget(tbl, e->xid);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case UPDATELOG:
|
case UPDATELOG:
|
||||||
|
@ -148,7 +151,7 @@ static void stasis_recovery_analysis(stasis_log_t* log) {
|
||||||
freeLogEntry(e);
|
freeLogEntry(e);
|
||||||
}
|
}
|
||||||
freeLogHandle(lh);
|
freeLogHandle(lh);
|
||||||
stasis_transaction_table_max_transaction_id_set(highestXid);
|
stasis_transaction_table_max_transaction_id_set(tbl, highestXid);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -168,7 +171,7 @@ static void stasis_recovery_analysis(stasis_log_t* log) {
|
||||||
Y (NTA replaces physical undo)
|
Y (NTA replaces physical undo)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static void stasis_recovery_redo(stasis_log_t* log) {
|
static void stasis_recovery_redo(stasis_log_t* log, stasis_transaction_table_t * tbl) {
|
||||||
LogHandle* lh = getLogHandle(log);
|
LogHandle* lh = getLogHandle(log);
|
||||||
const LogEntry * e;
|
const LogEntry * e;
|
||||||
|
|
||||||
|
@ -178,7 +181,7 @@ static void stasis_recovery_redo(stasis_log_t* log) {
|
||||||
// Is this log entry part of a transaction that needs to be redone?
|
// Is this log entry part of a transaction that needs to be redone?
|
||||||
if(pblHtLookup(transactionLSN, &(e->xid), sizeof(int)) != NULL) {
|
if(pblHtLookup(transactionLSN, &(e->xid), sizeof(int)) != NULL) {
|
||||||
if(e->type != INTERNALLOG) {
|
if(e->type != INTERNALLOG) {
|
||||||
stasis_transaction_table_roll_forward(e->xid, e->LSN, e->prevLSN);
|
stasis_transaction_table_roll_forward(tbl, e->xid, e->LSN, e->prevLSN);
|
||||||
}
|
}
|
||||||
// Check to see if this entry's action needs to be redone
|
// Check to see if this entry's action needs to be redone
|
||||||
switch(e->type) {
|
switch(e->type) {
|
||||||
|
@ -219,7 +222,7 @@ static void stasis_recovery_redo(stasis_log_t* log) {
|
||||||
} break;
|
} break;
|
||||||
case XCOMMIT:
|
case XCOMMIT:
|
||||||
{
|
{
|
||||||
stasis_transaction_table_forget(e->xid);
|
stasis_transaction_table_forget(tbl, e->xid);
|
||||||
|
|
||||||
if(globalLockManager.commit)
|
if(globalLockManager.commit)
|
||||||
globalLockManager.commit(e->xid);
|
globalLockManager.commit(e->xid);
|
||||||
|
@ -246,7 +249,7 @@ static void stasis_recovery_redo(stasis_log_t* log) {
|
||||||
freeLogHandle(lh);
|
freeLogHandle(lh);
|
||||||
|
|
||||||
}
|
}
|
||||||
static void stasis_recovery_undo(stasis_log_t* log, int recovery) {
|
static void stasis_recovery_undo(stasis_log_t* log, stasis_transaction_table_t * tbl, int recovery) {
|
||||||
LogHandle* lh;
|
LogHandle* lh;
|
||||||
|
|
||||||
DEBUG("Recovery: Undo\n");
|
DEBUG("Recovery: Undo\n");
|
||||||
|
@ -293,7 +296,7 @@ static void stasis_recovery_undo(stasis_log_t* log, int recovery) {
|
||||||
lsn_t clr_lsn = stasis_log_write_clr(log, e);
|
lsn_t clr_lsn = stasis_log_write_clr(log, e);
|
||||||
DEBUG("logged clr\n");
|
DEBUG("logged clr\n");
|
||||||
|
|
||||||
stasis_transaction_table_roll_forward(e->xid, e->LSN, e->prevLSN);
|
stasis_transaction_table_roll_forward(tbl, e->xid, e->LSN, e->prevLSN);
|
||||||
|
|
||||||
stasis_operation_undo(e, clr_lsn, p);
|
stasis_operation_undo(e, clr_lsn, p);
|
||||||
|
|
||||||
|
@ -331,7 +334,7 @@ static void stasis_recovery_undo(stasis_log_t* log, int recovery) {
|
||||||
prepared = 1;
|
prepared = 1;
|
||||||
|
|
||||||
stasis_transaction_table_roll_forward_with_reclsn
|
stasis_transaction_table_roll_forward_with_reclsn
|
||||||
(e->xid, e->LSN, e->prevLSN, getPrepareRecLSN(e));
|
(tbl, e->xid, e->LSN, e->prevLSN, getPrepareRecLSN(e));
|
||||||
} else {
|
} else {
|
||||||
DEBUG("xact was aborted\n");
|
DEBUG("xact was aborted\n");
|
||||||
}
|
}
|
||||||
|
@ -355,15 +358,15 @@ static void stasis_recovery_undo(stasis_log_t* log, int recovery) {
|
||||||
freeLogHandle(lh);
|
freeLogHandle(lh);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
void stasis_recovery_initiate(stasis_log_t* log, stasis_alloc_t * alloc) {
|
void stasis_recovery_initiate(stasis_log_t* log, stasis_transaction_table_t * tbl, stasis_alloc_t * alloc) {
|
||||||
|
|
||||||
transactionLSN = pblHtCreate();
|
transactionLSN = pblHtCreate();
|
||||||
DEBUG("Analysis started\n");
|
DEBUG("Analysis started\n");
|
||||||
stasis_recovery_analysis(log);
|
stasis_recovery_analysis(log, tbl);
|
||||||
DEBUG("Redo started\n");
|
DEBUG("Redo started\n");
|
||||||
stasis_recovery_redo(log);
|
stasis_recovery_redo(log, tbl);
|
||||||
DEBUG("Undo started\n");
|
DEBUG("Undo started\n");
|
||||||
stasis_recovery_undo(log,1);
|
stasis_recovery_undo(log, tbl, 1);
|
||||||
stasis_alloc_post_init(alloc);
|
stasis_alloc_post_init(alloc);
|
||||||
DEBUG("Recovery complete.\n");
|
DEBUG("Recovery complete.\n");
|
||||||
|
|
||||||
|
@ -377,7 +380,7 @@ void stasis_recovery_initiate(stasis_log_t* log, stasis_alloc_t * alloc) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void undoTrans(stasis_log_t* log, TransactionLog transaction) {
|
void undoTrans(stasis_log_t* log, stasis_transaction_table_t * tbl, stasis_transaction_table_entry_t transaction) {
|
||||||
|
|
||||||
pthread_mutex_lock(&rollback_mutex);
|
pthread_mutex_lock(&rollback_mutex);
|
||||||
assert(!rollbackLSNs);
|
assert(!rollbackLSNs);
|
||||||
|
@ -389,7 +392,7 @@ void undoTrans(stasis_log_t* log, TransactionLog transaction) {
|
||||||
/* Nothing to undo. (Happens for read-only xacts.) */
|
/* Nothing to undo. (Happens for read-only xacts.) */
|
||||||
}
|
}
|
||||||
|
|
||||||
stasis_recovery_undo(log, 0);
|
stasis_recovery_undo(log, tbl, 0);
|
||||||
if(rollbackLSNs) {
|
if(rollbackLSNs) {
|
||||||
destroyList(&rollbackLSNs);
|
destroyList(&rollbackLSNs);
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,181 +7,189 @@
|
||||||
#include <stasis/common.h>
|
#include <stasis/common.h>
|
||||||
#include <stasis/constants.h>
|
#include <stasis/constants.h>
|
||||||
#include <stasis/transactionTable.h>
|
#include <stasis/transactionTable.h>
|
||||||
|
#include <stasis/transactional.h>
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
|
|
||||||
TransactionLog stasis_transaction_table[MAX_TRANSACTIONS];
|
struct stasis_transaction_table_t {
|
||||||
static int stasis_transaction_table_active_count = 0;
|
int active_count;
|
||||||
static int stasis_transaction_table_xid_count = 0;
|
int xid_count;
|
||||||
|
/**
|
||||||
int stasis_transaction_table_num_active() {
|
This mutex protects the rest of the struct
|
||||||
return stasis_transaction_table_active_count;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
This mutex protects stasis_transaction_table, numActiveXactions and
|
|
||||||
xidCount.
|
xidCount.
|
||||||
*/
|
*/
|
||||||
static pthread_mutex_t stasis_transaction_table_mutex;
|
pthread_mutex_t mut;
|
||||||
|
stasis_transaction_table_entry_t table[MAX_TRANSACTIONS];
|
||||||
|
};
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
INVALID_XTABLE_XID = INVALID_XID,
|
INVALID_XTABLE_XID = INVALID_XID,
|
||||||
PENDING_XTABLE_XID = -2
|
PENDING_XTABLE_XID = -2
|
||||||
} stasis_transaction_table_status;
|
} stasis_transaction_table_status;
|
||||||
|
|
||||||
void stasis_transaction_table_init() {
|
int stasis_transaction_table_num_active(stasis_transaction_table_t *tbl) {
|
||||||
pthread_mutex_init(&stasis_transaction_table_mutex, NULL);
|
return tbl->active_count;
|
||||||
stasis_transaction_table_active_count = 0;
|
}
|
||||||
|
int stasis_transaction_table_is_active(stasis_transaction_table_t *tbl, int xid) {
|
||||||
|
return xid >= 0 && tbl->table[xid % MAX_TRANSACTIONS].xid == xid;
|
||||||
|
}
|
||||||
|
|
||||||
memset(stasis_transaction_table, INVALID_XTABLE_XID,
|
stasis_transaction_table_t * stasis_transaction_table_init() {
|
||||||
sizeof(TransactionLog)*MAX_TRANSACTIONS);
|
stasis_transaction_table_t * tbl = malloc(sizeof(*tbl));
|
||||||
|
pthread_mutex_init(&tbl->mut, NULL);
|
||||||
|
tbl->active_count = 0;
|
||||||
|
|
||||||
|
memset(tbl->table, INVALID_XTABLE_XID,
|
||||||
|
sizeof(stasis_transaction_table_entry_t)*MAX_TRANSACTIONS);
|
||||||
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
||||||
pthread_mutex_init(&stasis_transaction_table[i].mut,0);
|
pthread_mutex_init(&tbl->table[i].mut,0);
|
||||||
}
|
}
|
||||||
|
return tbl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void stasis_transaction_table_deinit() {
|
void stasis_transaction_table_deinit(stasis_transaction_table_t *tbl) {
|
||||||
pthread_mutex_destroy(&stasis_transaction_table_mutex);
|
pthread_mutex_destroy(&tbl->mut);
|
||||||
stasis_transaction_table_active_count = 0;
|
tbl->active_count = 0;
|
||||||
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
||||||
pthread_mutex_destroy(&stasis_transaction_table[i].mut);
|
pthread_mutex_destroy(&tbl->table[i].mut);
|
||||||
}
|
}
|
||||||
memset(stasis_transaction_table, INVALID_XTABLE_XID, sizeof(TransactionLog)*MAX_TRANSACTIONS);
|
free(tbl);
|
||||||
}
|
}
|
||||||
|
|
||||||
void stasis_transaction_table_max_transaction_id_set(int xid) {
|
void stasis_transaction_table_max_transaction_id_set(stasis_transaction_table_t *tbl, int xid) {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
stasis_transaction_table_xid_count = xid;
|
tbl->xid_count = xid;
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
}
|
}
|
||||||
void stasis_transaction_table_active_transaction_count_set(int xid) {
|
void stasis_transaction_table_active_transaction_count_set(stasis_transaction_table_t *tbl, int xid) {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
stasis_transaction_table_active_count = xid;
|
tbl->active_count = xid;
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
}
|
}
|
||||||
|
|
||||||
lsn_t stasis_transaction_table_minRecLSN() {
|
lsn_t stasis_transaction_table_minRecLSN(stasis_transaction_table_t *tbl) {
|
||||||
lsn_t minRecLSN = LSN_T_MAX;
|
lsn_t minRecLSN = LSN_T_MAX;
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
||||||
if(stasis_transaction_table[i].xid != INVALID_XTABLE_XID) {
|
if(tbl->table[i].xid != INVALID_XTABLE_XID) {
|
||||||
lsn_t recLSN = stasis_transaction_table[i].recLSN;
|
lsn_t recLSN = tbl->table[i].recLSN;
|
||||||
if(recLSN != -1 && recLSN < minRecLSN) {
|
if(recLSN != -1 && recLSN < minRecLSN) {
|
||||||
minRecLSN = recLSN;
|
minRecLSN = recLSN;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
return minRecLSN;
|
return minRecLSN;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int TactiveTransactionCount() {
|
int TactiveTransactionCount(stasis_transaction_table_t *tbl) {
|
||||||
return stasis_transaction_table_active_count;
|
return tbl->active_count;
|
||||||
}
|
}
|
||||||
|
|
||||||
int* stasis_transaction_table_list_active() {
|
int* stasis_transaction_table_list_active(stasis_transaction_table_t *tbl) {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
int * ret = malloc(sizeof(*ret));
|
int * ret = malloc(sizeof(*ret));
|
||||||
ret[0] = 0;
|
ret[0] = 0;
|
||||||
int retcount = 0;
|
int retcount = 0;
|
||||||
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
for(int i = 0; i < MAX_TRANSACTIONS; i++) {
|
||||||
if(stasis_transaction_table[i].xid != INVALID_XTABLE_XID) {
|
if(tbl->table[i].xid != INVALID_XTABLE_XID) {
|
||||||
ret[retcount] = stasis_transaction_table[i].xid;
|
ret[retcount] = tbl->table[i].xid;
|
||||||
retcount++;
|
retcount++;
|
||||||
ret = realloc(ret, (retcount+1) * sizeof(*ret));
|
ret = realloc(ret, (retcount+1) * sizeof(*ret));
|
||||||
ret[retcount] = 0;
|
ret[retcount] = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
int* TlistActiveTransactions() {
|
int* TlistActiveTransactions() {
|
||||||
return stasis_transaction_table_list_active();
|
return stasis_transaction_table_list_active(stasis_runtime_transaction_table());
|
||||||
}
|
}
|
||||||
int TisActiveTransaction(int xid) {
|
int TisActiveTransaction(int xid) {
|
||||||
if(xid < 0) { return 0; }
|
return stasis_transaction_table_is_active(stasis_runtime_transaction_table(), xid);
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
|
||||||
int ret = xid != INVALID_XTABLE_XID && stasis_transaction_table[xid%MAX_TRANSACTIONS].xid == xid;
|
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int stasis_transaction_table_roll_forward(int xid, lsn_t lsn, lsn_t prevLSN) {
|
int stasis_transaction_table_roll_forward(stasis_transaction_table_t *tbl, int xid, lsn_t lsn, lsn_t prevLSN) {
|
||||||
TransactionLog * l = &stasis_transaction_table[xid%MAX_TRANSACTIONS];
|
stasis_transaction_table_entry_t * l = &tbl->table[xid%MAX_TRANSACTIONS];
|
||||||
if(l->xid == xid) {
|
if(l->xid == xid) {
|
||||||
// rolling forward CLRs / NTAs makes prevLSN decrease.
|
// rolling forward CLRs / NTAs makes prevLSN decrease.
|
||||||
assert(l->prevLSN >= prevLSN);
|
assert(l->prevLSN >= prevLSN);
|
||||||
} else {
|
} else {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
assert(l->xid == INVALID_XTABLE_XID);
|
assert(l->xid == INVALID_XTABLE_XID);
|
||||||
l->xid = xid;
|
l->xid = xid;
|
||||||
l->recLSN = lsn;
|
l->recLSN = lsn;
|
||||||
stasis_transaction_table_active_count++;
|
tbl->active_count++;
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
}
|
}
|
||||||
l->prevLSN = lsn;
|
l->prevLSN = lsn;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
int stasis_transaction_table_roll_forward_with_reclsn(int xid, lsn_t lsn,
|
int stasis_transaction_table_roll_forward_with_reclsn(stasis_transaction_table_t *tbl, int xid, lsn_t lsn,
|
||||||
lsn_t prevLSN,
|
lsn_t prevLSN,
|
||||||
lsn_t recLSN) {
|
lsn_t recLSN) {
|
||||||
assert(stasis_transaction_table[xid%MAX_TRANSACTIONS].recLSN == recLSN);
|
assert(tbl->table[xid%MAX_TRANSACTIONS].recLSN == recLSN);
|
||||||
return stasis_transaction_table_roll_forward(xid, lsn, prevLSN);
|
return stasis_transaction_table_roll_forward(tbl, xid, lsn, prevLSN);
|
||||||
}
|
}
|
||||||
TransactionLog * stasis_transaction_table_begin(int * xid) {
|
|
||||||
|
stasis_transaction_table_entry_t * stasis_transaction_table_begin(stasis_transaction_table_t *tbl, int * xid) {
|
||||||
int index = 0;
|
int index = 0;
|
||||||
int xidCount_tmp;
|
int xidCount_tmp;
|
||||||
|
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
|
|
||||||
if( stasis_transaction_table_active_count == MAX_TRANSACTIONS ) {
|
if( tbl->active_count == MAX_TRANSACTIONS ) {
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
*xid = LLADD_EXCEED_MAX_TRANSACTIONS;
|
*xid = LLADD_EXCEED_MAX_TRANSACTIONS;
|
||||||
return 0;
|
return 0;
|
||||||
} else {
|
} else {
|
||||||
DEBUG("%s:%d activate in begin\n",__FILE__,__LINE__);
|
DEBUG("%s:%d activate in begin\n",__FILE__,__LINE__);
|
||||||
stasis_transaction_table_active_count++;
|
tbl->active_count++;
|
||||||
}
|
}
|
||||||
for(int i = 0; i < MAX_TRANSACTIONS; i++ ) {
|
for(int i = 0; i < MAX_TRANSACTIONS; i++ ) {
|
||||||
stasis_transaction_table_xid_count++;
|
tbl->xid_count++;
|
||||||
if( stasis_transaction_table[stasis_transaction_table_xid_count%MAX_TRANSACTIONS].xid == INVALID_XTABLE_XID ) {
|
if( tbl->table[tbl->xid_count%MAX_TRANSACTIONS].xid == INVALID_XTABLE_XID ) {
|
||||||
index = stasis_transaction_table_xid_count%MAX_TRANSACTIONS;
|
index = tbl->xid_count%MAX_TRANSACTIONS;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
xidCount_tmp = stasis_transaction_table_xid_count;
|
xidCount_tmp = tbl->xid_count;
|
||||||
|
|
||||||
stasis_transaction_table[index].xid = PENDING_XTABLE_XID;
|
tbl->table[index].xid = PENDING_XTABLE_XID;
|
||||||
|
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
*xid = xidCount_tmp;
|
*xid = xidCount_tmp;
|
||||||
return &stasis_transaction_table[index];
|
return &tbl->table[index];
|
||||||
}
|
}
|
||||||
TransactionLog * stasis_transaction_table_get(int xid) {
|
stasis_transaction_table_entry_t * stasis_transaction_table_get(stasis_transaction_table_t *tbl, int xid) {
|
||||||
return &stasis_transaction_table[xid % MAX_TRANSACTIONS];
|
if(tbl->table[xid % MAX_TRANSACTIONS].xid == xid) {
|
||||||
|
return &tbl->table[xid % MAX_TRANSACTIONS];
|
||||||
|
} else {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
int stasis_transaction_table_commit(int xid) {
|
int stasis_transaction_table_commit(stasis_transaction_table_t *tbl, int xid) {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
|
|
||||||
stasis_transaction_table[xid%MAX_TRANSACTIONS].xid = INVALID_XTABLE_XID;
|
tbl->table[xid%MAX_TRANSACTIONS].xid = INVALID_XTABLE_XID;
|
||||||
DEBUG("%s:%d deactivate %d\n",__FILE__,__LINE__,xid);
|
DEBUG("%s:%d deactivate %d\n",__FILE__,__LINE__,xid);
|
||||||
stasis_transaction_table_active_count--;
|
tbl->active_count--;
|
||||||
assert( stasis_transaction_table_active_count >= 0 );
|
assert( tbl->active_count >= 0 );
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
int stasis_transaction_table_forget(int xid) {
|
int stasis_transaction_table_forget(stasis_transaction_table_t *tbl, int xid) {
|
||||||
assert(xid != INVALID_XTABLE_XID);
|
assert(xid != INVALID_XTABLE_XID);
|
||||||
TransactionLog * l = &stasis_transaction_table[xid%MAX_TRANSACTIONS];
|
stasis_transaction_table_entry_t * l = &tbl->table[xid%MAX_TRANSACTIONS];
|
||||||
if(l->xid == xid) {
|
if(l->xid == xid) {
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
pthread_mutex_lock(&tbl->mut);
|
||||||
l->xid = INVALID_XTABLE_XID;
|
l->xid = INVALID_XTABLE_XID;
|
||||||
l->prevLSN = -1;
|
l->prevLSN = -1;
|
||||||
l->recLSN = -1;
|
l->recLSN = -1;
|
||||||
stasis_transaction_table_active_count--;
|
tbl->active_count--;
|
||||||
assert(stasis_transaction_table_active_count >= 0);
|
assert(tbl->active_count >= 0);
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
pthread_mutex_unlock(&tbl->mut);
|
||||||
} else {
|
} else {
|
||||||
assert(l->xid == INVALID_XTABLE_XID);
|
assert(l->xid == INVALID_XTABLE_XID);
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,7 +29,8 @@
|
||||||
static int stasis_initted = 0;
|
static int stasis_initted = 0;
|
||||||
|
|
||||||
static stasis_log_t* stasis_log_file = 0;
|
static stasis_log_t* stasis_log_file = 0;
|
||||||
stasis_dirty_page_table_t * stasis_dirty_page_table = 0;
|
static stasis_dirty_page_table_t * stasis_dirty_page_table = 0;
|
||||||
|
static stasis_transaction_table_t * stasis_transaction_table;
|
||||||
static stasis_truncation_t * stasis_truncation = 0;
|
static stasis_truncation_t * stasis_truncation = 0;
|
||||||
static stasis_alloc_t * stasis_alloc = 0;
|
static stasis_alloc_t * stasis_alloc = 0;
|
||||||
static stasis_allocation_policy_t * stasis_allocation_policy = 0;
|
static stasis_allocation_policy_t * stasis_allocation_policy = 0;
|
||||||
|
@ -38,10 +39,12 @@ static stasis_buffer_manager_t * stasis_buffer_manager = 0;
|
||||||
void * stasis_runtime_buffer_manager() {
|
void * stasis_runtime_buffer_manager() {
|
||||||
return stasis_buffer_manager;
|
return stasis_buffer_manager;
|
||||||
}
|
}
|
||||||
|
|
||||||
void * stasis_runtime_dirty_page_table() {
|
void * stasis_runtime_dirty_page_table() {
|
||||||
return stasis_dirty_page_table;
|
return stasis_dirty_page_table;
|
||||||
}
|
}
|
||||||
|
void * stasis_runtime_transaction_table() {
|
||||||
|
return stasis_transaction_table;
|
||||||
|
}
|
||||||
void * stasis_runtime_alloc_state() {
|
void * stasis_runtime_alloc_state() {
|
||||||
return stasis_alloc;
|
return stasis_alloc;
|
||||||
}
|
}
|
||||||
|
@ -63,7 +66,6 @@ int Tinit() {
|
||||||
|
|
||||||
compensations_init();
|
compensations_init();
|
||||||
|
|
||||||
stasis_transaction_table_init();
|
|
||||||
stasis_operation_table_init();
|
stasis_operation_table_init();
|
||||||
|
|
||||||
stasis_log_file = 0;
|
stasis_log_file = 0;
|
||||||
|
@ -82,7 +84,9 @@ int Tinit() {
|
||||||
assert(stasis_log_file != NULL);
|
assert(stasis_log_file != NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
stasis_transaction_table = stasis_transaction_table_init();
|
||||||
stasis_dirty_page_table = stasis_dirty_page_table_init();
|
stasis_dirty_page_table = stasis_dirty_page_table_init();
|
||||||
|
|
||||||
stasis_page_init(stasis_dirty_page_table);
|
stasis_page_init(stasis_dirty_page_table);
|
||||||
|
|
||||||
stasis_buffer_manager = stasis_buffer_manager_factory(stasis_log_file, stasis_dirty_page_table);
|
stasis_buffer_manager = stasis_buffer_manager_factory(stasis_log_file, stasis_dirty_page_table);
|
||||||
|
@ -101,8 +105,9 @@ int Tinit() {
|
||||||
setupLockManagerCallbacksNil();
|
setupLockManagerCallbacksNil();
|
||||||
//setupLockManagerCallbacksPage();
|
//setupLockManagerCallbacksPage();
|
||||||
|
|
||||||
stasis_recovery_initiate(stasis_log_file, stasis_alloc);
|
stasis_recovery_initiate(stasis_log_file, stasis_transaction_table, stasis_alloc);
|
||||||
stasis_truncation = stasis_truncation_init(stasis_dirty_page_table, stasis_buffer_manager, stasis_log_file);
|
stasis_truncation = stasis_truncation_init(stasis_dirty_page_table, stasis_transaction_table,
|
||||||
|
stasis_buffer_manager, stasis_log_file);
|
||||||
if(stasis_truncation_automatic) {
|
if(stasis_truncation_automatic) {
|
||||||
// should this be before InitiateRecovery?
|
// should this be before InitiateRecovery?
|
||||||
stasis_truncation_thread_start(stasis_truncation);
|
stasis_truncation_thread_start(stasis_truncation);
|
||||||
|
@ -118,7 +123,7 @@ int Tbegin() {
|
||||||
|
|
||||||
int xid;
|
int xid;
|
||||||
|
|
||||||
TransactionLog* newXact = stasis_transaction_table_begin(&xid);
|
stasis_transaction_table_entry_t* newXact = stasis_transaction_table_begin(stasis_transaction_table, &xid);
|
||||||
if(newXact != 0) {
|
if(newXact != 0) {
|
||||||
stasis_log_begin_transaction(stasis_log_file, xid, newXact);
|
stasis_log_begin_transaction(stasis_log_file, xid, newXact);
|
||||||
|
|
||||||
|
@ -136,8 +141,8 @@ compensated_function void Tupdate(int xid, pageid_t page,
|
||||||
assert(stasis_initted);
|
assert(stasis_initted);
|
||||||
assert(page != INVALID_PAGE);
|
assert(page != INVALID_PAGE);
|
||||||
LogEntry * e;
|
LogEntry * e;
|
||||||
assert(xid >= 0 && stasis_transaction_table[xid % MAX_TRANSACTIONS].xid == xid);
|
stasis_transaction_table_entry_t * xact = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
|
assert(xact);
|
||||||
Page * p = loadPageForOperation(xid, page, op);
|
Page * p = loadPageForOperation(xid, page, op);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
@ -148,10 +153,9 @@ compensated_function void Tupdate(int xid, pageid_t page,
|
||||||
|
|
||||||
if(p) writelock(p->rwlatch,0);
|
if(p) writelock(p->rwlatch,0);
|
||||||
|
|
||||||
e = stasis_log_write_update(stasis_log_file, &stasis_transaction_table[xid % MAX_TRANSACTIONS],
|
e = stasis_log_write_update(stasis_log_file, xact, page, op, dat, datlen);
|
||||||
page, op, dat, datlen);
|
|
||||||
|
|
||||||
assert(stasis_transaction_table[xid % MAX_TRANSACTIONS].prevLSN == e->LSN);
|
assert(xact->prevLSN == e->LSN);
|
||||||
DEBUG("Tupdate() e->LSN: %ld\n", e->LSN);
|
DEBUG("Tupdate() e->LSN: %ld\n", e->LSN);
|
||||||
stasis_operation_do(e, p);
|
stasis_operation_do(e, p);
|
||||||
freeLogEntry(e);
|
freeLogEntry(e);
|
||||||
|
@ -163,7 +167,7 @@ compensated_function void Tupdate(int xid, pageid_t page,
|
||||||
void TreorderableUpdate(int xid, void * hp, pageid_t page,
|
void TreorderableUpdate(int xid, void * hp, pageid_t page,
|
||||||
const void *dat, size_t datlen, int op) {
|
const void *dat, size_t datlen, int op) {
|
||||||
stasis_log_reordering_handle_t * h = (typeof(h))hp;
|
stasis_log_reordering_handle_t * h = (typeof(h))hp;
|
||||||
assert(xid >= 0 && stasis_transaction_table[xid % MAX_TRANSACTIONS].xid == xid);
|
assert(stasis_transaction_table_is_active(stasis_transaction_table, xid));
|
||||||
Page * p = loadPage(xid, page);
|
Page * p = loadPage(xid, page);
|
||||||
assert(p);
|
assert(p);
|
||||||
try {
|
try {
|
||||||
|
@ -190,9 +194,8 @@ void TreorderableUpdate(int xid, void * hp, pageid_t page,
|
||||||
}
|
}
|
||||||
lsn_t TwritebackUpdate(int xid, pageid_t page,
|
lsn_t TwritebackUpdate(int xid, pageid_t page,
|
||||||
const void *dat, size_t datlen, int op) {
|
const void *dat, size_t datlen, int op) {
|
||||||
assert(xid >= 0 && stasis_transaction_table[xid % MAX_TRANSACTIONS].xid == xid);
|
|
||||||
LogEntry * e = allocUpdateLogEntry(-1, xid, op, page, dat, datlen);
|
LogEntry * e = allocUpdateLogEntry(-1, xid, op, page, dat, datlen);
|
||||||
TransactionLog* l = &stasis_transaction_table[xid % MAX_TRANSACTIONS];
|
stasis_transaction_table_entry_t* l = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
stasis_log_file->write_entry(stasis_log_file, e);
|
stasis_log_file->write_entry(stasis_log_file, e);
|
||||||
|
|
||||||
if(l->prevLSN == -1) { l->recLSN = e->LSN; }
|
if(l->prevLSN == -1) { l->recLSN = e->LSN; }
|
||||||
|
@ -208,7 +211,7 @@ void TreorderableWritebackUpdate(int xid, void* hp,
|
||||||
pageid_t page, const void * dat,
|
pageid_t page, const void * dat,
|
||||||
size_t datlen, int op) {
|
size_t datlen, int op) {
|
||||||
stasis_log_reordering_handle_t* h = hp;
|
stasis_log_reordering_handle_t* h = hp;
|
||||||
assert(xid >= 0 && stasis_transaction_table[xid % MAX_TRANSACTIONS].xid == xid);
|
assert(stasis_transaction_table_is_active(stasis_transaction_table, xid));
|
||||||
pthread_mutex_lock(&h->mut);
|
pthread_mutex_lock(&h->mut);
|
||||||
LogEntry * e = allocUpdateLogEntry(-1, xid, op, page, dat, datlen);
|
LogEntry * e = allocUpdateLogEntry(-1, xid, op, page, dat, datlen);
|
||||||
stasis_log_reordering_handle_append(h, 0, op, dat, datlen, sizeofLogEntry(0, e));
|
stasis_log_reordering_handle_append(h, 0, op, dat, datlen, sizeofLogEntry(0, e));
|
||||||
|
@ -264,22 +267,18 @@ compensated_function void TreadRaw(int xid, recordid rid, void * dat) {
|
||||||
static inline int TcommitHelper(int xid, int force) {
|
static inline int TcommitHelper(int xid, int force) {
|
||||||
lsn_t lsn;
|
lsn_t lsn;
|
||||||
assert(xid >= 0);
|
assert(xid >= 0);
|
||||||
#ifdef DEBUGGING
|
|
||||||
pthread_mutex_lock(&stasis_transaction_table_mutex);
|
|
||||||
assert(stasis_transaction_table_num_active <= MAX_TRANSACTIONS);
|
|
||||||
pthread_mutex_unlock(&stasis_transaction_table_mutex);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if(stasis_transaction_table[xid % MAX_TRANSACTIONS].prevLSN != INVALID_LSN) {
|
stasis_transaction_table_entry_t * xact = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
|
if(xact->prevLSN != INVALID_LSN) {
|
||||||
|
|
||||||
lsn = stasis_log_commit_transaction(stasis_log_file, &stasis_transaction_table[xid % MAX_TRANSACTIONS], force);
|
lsn = stasis_log_commit_transaction(stasis_log_file, xact, force);
|
||||||
if(globalLockManager.commit) { globalLockManager.commit(xid); }
|
if(globalLockManager.commit) { globalLockManager.commit(xid); }
|
||||||
|
|
||||||
stasis_alloc_committed(stasis_alloc, xid);
|
stasis_alloc_committed(stasis_alloc, xid);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
stasis_transaction_table_commit(xid);
|
stasis_transaction_table_commit(stasis_transaction_table, xid);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -296,9 +295,9 @@ void TforceCommits() {
|
||||||
|
|
||||||
int Tprepare(int xid) {
|
int Tprepare(int xid) {
|
||||||
assert(xid >= 0);
|
assert(xid >= 0);
|
||||||
off_t i = xid % MAX_TRANSACTIONS;
|
stasis_transaction_table_entry_t * xact = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
assert(stasis_transaction_table[i].xid == xid);
|
assert(xact);
|
||||||
stasis_log_prepare_transaction(stasis_log_file, &stasis_transaction_table[i]);
|
stasis_log_prepare_transaction(stasis_log_file, xact);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -306,13 +305,13 @@ int Tabort(int xid) {
|
||||||
lsn_t lsn;
|
lsn_t lsn;
|
||||||
assert(xid >= 0);
|
assert(xid >= 0);
|
||||||
|
|
||||||
TransactionLog * t =&stasis_transaction_table[xid%MAX_TRANSACTIONS];
|
stasis_transaction_table_entry_t * t = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
assert(t->xid == xid);
|
assert(t->xid == xid);
|
||||||
|
|
||||||
lsn = stasis_log_abort_transaction(stasis_log_file, t);
|
lsn = stasis_log_abort_transaction(stasis_log_file, t);
|
||||||
|
|
||||||
/** @todo is the order of the next two calls important? */
|
/** @todo is the order of the next two calls important? */
|
||||||
undoTrans(stasis_log_file, *t);
|
undoTrans(stasis_log_file, stasis_transaction_table, *t); // XXX don't really need to pass the whole table in...
|
||||||
if(globalLockManager.abort) { globalLockManager.abort(xid); }
|
if(globalLockManager.abort) { globalLockManager.abort(xid); }
|
||||||
|
|
||||||
stasis_alloc_aborted(stasis_alloc, xid);
|
stasis_alloc_aborted(stasis_alloc, xid);
|
||||||
|
@ -320,25 +319,24 @@ int Tabort(int xid) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
int Tforget(int xid) {
|
int Tforget(int xid) {
|
||||||
TransactionLog * t = &stasis_transaction_table[xid%MAX_TRANSACTIONS];
|
stasis_transaction_table_entry_t * t = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
assert(t->xid == xid);
|
assert(t->xid == xid);
|
||||||
stasis_log_end_aborted_transaction(stasis_log_file, t);
|
stasis_log_end_aborted_transaction(stasis_log_file, t);
|
||||||
stasis_transaction_table_forget(t->xid);
|
stasis_transaction_table_forget(stasis_transaction_table, t->xid);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
int Tdeinit() {
|
int Tdeinit() {
|
||||||
|
|
||||||
int * active = stasis_transaction_table_list_active();
|
int * active = stasis_transaction_table_list_active(stasis_transaction_table);
|
||||||
int count = stasis_transaction_table_num_active();
|
int count = stasis_transaction_table_num_active(stasis_transaction_table);
|
||||||
|
|
||||||
for(int i = 0; i < count; i++) {
|
for(int i = 0; i < count; i++) {
|
||||||
if(!stasis_suppress_unclean_shutdown_warnings) {
|
if(!stasis_suppress_unclean_shutdown_warnings) {
|
||||||
fprintf(stderr, "WARNING: Tdeinit() is aborting transaction %d\n",
|
fprintf(stderr, "WARNING: Tdeinit() is aborting transaction %d\n", active[i]);
|
||||||
stasis_transaction_table[i].xid);
|
|
||||||
}
|
}
|
||||||
Tabort(active[i]);
|
Tabort(active[i]);
|
||||||
}
|
}
|
||||||
assert( stasis_transaction_table_num_active() == 0 );
|
assert( stasis_transaction_table_num_active(stasis_transaction_table) == 0 );
|
||||||
|
|
||||||
free(active);
|
free(active);
|
||||||
|
|
||||||
|
@ -352,7 +350,7 @@ int Tdeinit() {
|
||||||
stasis_log_group_force_t * group_force = stasis_log_file->group_force;
|
stasis_log_group_force_t * group_force = stasis_log_file->group_force;
|
||||||
stasis_log_file->close(stasis_log_file);
|
stasis_log_file->close(stasis_log_file);
|
||||||
if(group_force) { stasis_log_group_force_deinit(group_force); }
|
if(group_force) { stasis_log_group_force_deinit(group_force); }
|
||||||
stasis_transaction_table_deinit();
|
stasis_transaction_table_deinit(stasis_transaction_table);
|
||||||
stasis_dirty_page_table_deinit(stasis_dirty_page_table);
|
stasis_dirty_page_table_deinit(stasis_dirty_page_table);
|
||||||
|
|
||||||
stasis_initted = 0;
|
stasis_initted = 0;
|
||||||
|
@ -373,7 +371,7 @@ int TuncleanShutdown() {
|
||||||
// XXX: close_file?
|
// XXX: close_file?
|
||||||
stasis_page_deinit();
|
stasis_page_deinit();
|
||||||
stasis_log_file->close(stasis_log_file);
|
stasis_log_file->close(stasis_log_file);
|
||||||
stasis_transaction_table_deinit();
|
stasis_transaction_table_deinit(stasis_transaction_table);
|
||||||
stasis_dirty_page_table_deinit(stasis_dirty_page_table);
|
stasis_dirty_page_table_deinit(stasis_dirty_page_table);
|
||||||
|
|
||||||
// Reset it here so the warnings will appear if a new stasis
|
// Reset it here so the warnings will appear if a new stasis
|
||||||
|
@ -401,14 +399,15 @@ typedef struct {
|
||||||
} stasis_nta_handle;
|
} stasis_nta_handle;
|
||||||
|
|
||||||
int TnestedTopAction(int xid, int op, const byte * dat, size_t datSize) {
|
int TnestedTopAction(int xid, int op, const byte * dat, size_t datSize) {
|
||||||
|
stasis_transaction_table_entry_t * xact = stasis_transaction_table_get(stasis_transaction_table, xid);
|
||||||
assert(xid >= 0);
|
assert(xid >= 0);
|
||||||
void * e = stasis_log_begin_nta(stasis_log_file,
|
void * e = stasis_log_begin_nta(stasis_log_file,
|
||||||
&stasis_transaction_table[xid % MAX_TRANSACTIONS],
|
xact,
|
||||||
op, dat, datSize);
|
op, dat, datSize);
|
||||||
// HACK: breaks encapsulation.
|
// HACK: breaks encapsulation.
|
||||||
stasis_operation_do(e, NULL);
|
stasis_operation_do(e, NULL);
|
||||||
|
|
||||||
stasis_log_end_nta(stasis_log_file, &stasis_transaction_table[xid % MAX_TRANSACTIONS], e);
|
stasis_log_end_nta(stasis_log_file, xact, e);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -416,7 +415,7 @@ int TnestedTopAction(int xid, int op, const byte * dat, size_t datSize) {
|
||||||
void * TbeginNestedTopAction(int xid, int op, const byte * dat, int datSize) {
|
void * TbeginNestedTopAction(int xid, int op, const byte * dat, int datSize) {
|
||||||
assert(xid >= 0);
|
assert(xid >= 0);
|
||||||
|
|
||||||
void * ret = stasis_log_begin_nta(stasis_log_file, &stasis_transaction_table[xid % MAX_TRANSACTIONS], op, dat, datSize);
|
void * ret = stasis_log_begin_nta(stasis_log_file, stasis_transaction_table_get(stasis_transaction_table, xid), op, dat, datSize);
|
||||||
DEBUG("Begin Nested Top Action e->LSN: %ld\n", e->LSN);
|
DEBUG("Begin Nested Top Action e->LSN: %ld\n", e->LSN);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@ -427,7 +426,7 @@ void * TbeginNestedTopAction(int xid, int op, const byte * dat, int datSize) {
|
||||||
*/
|
*/
|
||||||
lsn_t TendNestedTopAction(int xid, void * handle) {
|
lsn_t TendNestedTopAction(int xid, void * handle) {
|
||||||
|
|
||||||
lsn_t ret = stasis_log_end_nta(stasis_log_file, &stasis_transaction_table[xid % MAX_TRANSACTIONS], handle);
|
lsn_t ret = stasis_log_end_nta(stasis_log_file, stasis_transaction_table_get(stasis_transaction_table, xid), handle);
|
||||||
|
|
||||||
DEBUG("NestedTopAction CLR %d, LSN: %ld type: %ld (undoing: %ld, next to undo: %ld)\n", e->xid,
|
DEBUG("NestedTopAction CLR %d, LSN: %ld type: %ld (undoing: %ld, next to undo: %ld)\n", e->xid,
|
||||||
clrLSN, undoneLSN, *prevLSN);
|
clrLSN, undoneLSN, *prevLSN);
|
||||||
|
|
|
@ -11,6 +11,7 @@ struct stasis_truncation_t {
|
||||||
pthread_mutex_t shutdown_mutex;
|
pthread_mutex_t shutdown_mutex;
|
||||||
pthread_cond_t shutdown_cond;
|
pthread_cond_t shutdown_cond;
|
||||||
stasis_dirty_page_table_t * dirty_pages;
|
stasis_dirty_page_table_t * dirty_pages;
|
||||||
|
stasis_transaction_table_t * transaction_table;
|
||||||
stasis_buffer_manager_t * buffer_manager;
|
stasis_buffer_manager_t * buffer_manager;
|
||||||
stasis_log_t * log;
|
stasis_log_t * log;
|
||||||
};
|
};
|
||||||
|
@ -24,13 +25,15 @@ struct stasis_truncation_t {
|
||||||
#define TRUNCATE_INTERVAL 1
|
#define TRUNCATE_INTERVAL 1
|
||||||
#define MIN_INCREMENTAL_TRUNCATION (1024 * 1024 * 25)
|
#define MIN_INCREMENTAL_TRUNCATION (1024 * 1024 * 25)
|
||||||
#endif
|
#endif
|
||||||
stasis_truncation_t * stasis_truncation_init(stasis_dirty_page_table_t * dpt, stasis_buffer_manager_t *buffer_manager, stasis_log_t *log) {
|
stasis_truncation_t * stasis_truncation_init(stasis_dirty_page_table_t * dpt, stasis_transaction_table_t * tbl,
|
||||||
|
stasis_buffer_manager_t *buffer_manager, stasis_log_t *log) {
|
||||||
stasis_truncation_t * ret = malloc(sizeof(*ret));
|
stasis_truncation_t * ret = malloc(sizeof(*ret));
|
||||||
ret->initialized = 1;
|
ret->initialized = 1;
|
||||||
ret->automaticallyTruncating = 0;
|
ret->automaticallyTruncating = 0;
|
||||||
pthread_mutex_init(&ret->shutdown_mutex, 0);
|
pthread_mutex_init(&ret->shutdown_mutex, 0);
|
||||||
pthread_cond_init(&ret->shutdown_cond, 0);
|
pthread_cond_init(&ret->shutdown_cond, 0);
|
||||||
ret->dirty_pages = dpt;
|
ret->dirty_pages = dpt;
|
||||||
|
ret->transaction_table = tbl;
|
||||||
ret->buffer_manager = buffer_manager;
|
ret->buffer_manager = buffer_manager;
|
||||||
ret->log = log;
|
ret->log = log;
|
||||||
return ret;
|
return ret;
|
||||||
|
@ -92,7 +95,7 @@ int stasis_truncation_truncate(stasis_truncation_t* trunc, int force) {
|
||||||
//dirty pages.
|
//dirty pages.
|
||||||
|
|
||||||
lsn_t page_rec_lsn = stasis_dirty_page_table_minRecLSN(trunc->dirty_pages);
|
lsn_t page_rec_lsn = stasis_dirty_page_table_minRecLSN(trunc->dirty_pages);
|
||||||
lsn_t xact_rec_lsn = stasis_transaction_table_minRecLSN();
|
lsn_t xact_rec_lsn = stasis_transaction_table_minRecLSN(trunc->transaction_table);
|
||||||
lsn_t flushed_lsn = trunc->log->first_unstable_lsn(trunc->log, LOG_FORCE_WAL);
|
lsn_t flushed_lsn = trunc->log->first_unstable_lsn(trunc->log, LOG_FORCE_WAL);
|
||||||
|
|
||||||
lsn_t rec_lsn = page_rec_lsn < xact_rec_lsn ? page_rec_lsn : xact_rec_lsn;
|
lsn_t rec_lsn = page_rec_lsn < xact_rec_lsn ? page_rec_lsn : xact_rec_lsn;
|
||||||
|
|
|
@ -266,7 +266,7 @@ void stasis_log_force(stasis_log_t* log, lsn_t lsn, stasis_log_force_mode_t mode
|
||||||
Inform the logging layer that a new transaction has begun, and
|
Inform the logging layer that a new transaction has begun, and
|
||||||
obtain a handle.
|
obtain a handle.
|
||||||
*/
|
*/
|
||||||
void stasis_log_begin_transaction(stasis_log_t* log, int xid, TransactionLog* l);
|
void stasis_log_begin_transaction(stasis_log_t* log, int xid, stasis_transaction_table_entry_t* l);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Write a transaction PREPARE to the log tail. Blocks until the
|
Write a transaction PREPARE to the log tail. Blocks until the
|
||||||
|
@ -274,27 +274,27 @@ void stasis_log_begin_transaction(stasis_log_t* log, int xid, TransactionLog* l)
|
||||||
|
|
||||||
@return the lsn of the prepare log entry
|
@return the lsn of the prepare log entry
|
||||||
*/
|
*/
|
||||||
lsn_t stasis_log_prepare_transaction(stasis_log_t* log, TransactionLog * l);
|
lsn_t stasis_log_prepare_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l);
|
||||||
/**
|
/**
|
||||||
Write a transaction COMMIT to the log tail. Blocks until the commit
|
Write a transaction COMMIT to the log tail. Blocks until the commit
|
||||||
record is stable.
|
record is stable.
|
||||||
|
|
||||||
@return the lsn of the commit log entry.
|
@return the lsn of the commit log entry.
|
||||||
*/
|
*/
|
||||||
lsn_t stasis_log_commit_transaction(stasis_log_t* log, TransactionLog * l, int force);
|
lsn_t stasis_log_commit_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l, int force);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Write a transaction ABORT to the log tail. Does not force the log.
|
Write a transaction ABORT to the log tail. Does not force the log.
|
||||||
|
|
||||||
@return the lsn of the abort log entry.
|
@return the lsn of the abort log entry.
|
||||||
*/
|
*/
|
||||||
lsn_t stasis_log_abort_transaction(stasis_log_t* log, TransactionLog * l);
|
lsn_t stasis_log_abort_transaction(stasis_log_t* log, stasis_transaction_table_entry_t * l);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Write a end transaction record. This entry tells recovery's undo
|
Write a end transaction record. This entry tells recovery's undo
|
||||||
phase that it may safely ignore the transaction.
|
phase that it may safely ignore the transaction.
|
||||||
*/
|
*/
|
||||||
lsn_t stasis_log_end_aborted_transaction (stasis_log_t* log, TransactionLog * l);
|
lsn_t stasis_log_end_aborted_transaction (stasis_log_t* log, stasis_transaction_table_entry_t * l);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
stasis_log_write_update writes an UPDATELOG log record to the log tail. It
|
stasis_log_write_update writes an UPDATELOG log record to the log tail. It
|
||||||
|
@ -303,7 +303,7 @@ lsn_t stasis_log_end_aborted_transaction (stasis_log_t* log, TransactionLog * l)
|
||||||
state of the parameter l.
|
state of the parameter l.
|
||||||
*/
|
*/
|
||||||
LogEntry * stasis_log_write_update(stasis_log_t* log,
|
LogEntry * stasis_log_write_update(stasis_log_t* log,
|
||||||
TransactionLog * l, pageid_t page, unsigned int operation,
|
stasis_transaction_table_entry_t * l, pageid_t page, unsigned int operation,
|
||||||
const byte * arg, size_t arg_size);
|
const byte * arg, size_t arg_size);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -319,7 +319,7 @@ lsn_t stasis_log_write_clr(stasis_log_t* log, const LogEntry * e);
|
||||||
|
|
||||||
lsn_t stasis_log_write_dummy_clr(stasis_log_t* log, int xid, lsn_t prev_lsn);
|
lsn_t stasis_log_write_dummy_clr(stasis_log_t* log, int xid, lsn_t prev_lsn);
|
||||||
|
|
||||||
LogEntry * stasis_log_begin_nta(stasis_log_t* log, TransactionLog * l, unsigned int op,
|
LogEntry * stasis_log_begin_nta(stasis_log_t* log, stasis_transaction_table_entry_t * l, unsigned int op,
|
||||||
const byte * arg, size_t arg_size);
|
const byte * arg, size_t arg_size);
|
||||||
lsn_t stasis_log_end_nta(stasis_log_t* log, TransactionLog * l, LogEntry * e);
|
lsn_t stasis_log_end_nta(stasis_log_t* log, stasis_transaction_table_entry_t * l, LogEntry * e);
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -13,7 +13,7 @@ typedef struct {
|
||||||
} stasis_log_reordering_op_t;
|
} stasis_log_reordering_op_t;
|
||||||
|
|
||||||
typedef struct stasis_log_reordering_handle_t {
|
typedef struct stasis_log_reordering_handle_t {
|
||||||
TransactionLog *l;
|
stasis_transaction_table_entry_t *l;
|
||||||
stasis_log_t * log;
|
stasis_log_t * log;
|
||||||
pthread_mutex_t mut;
|
pthread_mutex_t mut;
|
||||||
pthread_cond_t done;
|
pthread_cond_t done;
|
||||||
|
@ -34,7 +34,7 @@ typedef struct stasis_log_reordering_handle_t {
|
||||||
void stasis_log_reordering_handle_flush(stasis_log_reordering_handle_t * h);
|
void stasis_log_reordering_handle_flush(stasis_log_reordering_handle_t * h);
|
||||||
void stasis_log_reordering_handle_close(stasis_log_reordering_handle_t * h);
|
void stasis_log_reordering_handle_close(stasis_log_reordering_handle_t * h);
|
||||||
stasis_log_reordering_handle_t *
|
stasis_log_reordering_handle_t *
|
||||||
stasis_log_reordering_handle_open(TransactionLog * l,
|
stasis_log_reordering_handle_open(stasis_transaction_table_entry_t * l,
|
||||||
stasis_log_t* log,
|
stasis_log_t* log,
|
||||||
size_t chunk_len,
|
size_t chunk_len,
|
||||||
size_t max_len,
|
size_t max_len,
|
||||||
|
|
|
@ -1,11 +1,15 @@
|
||||||
#ifndef __LLADD_RECOVERY2_H
|
#ifndef __LLADD_RECOVERY2_H
|
||||||
#define __LLADD_RECOVERY2_H
|
#define __LLADD_RECOVERY2_H
|
||||||
|
|
||||||
|
#include <stasis/transactionTable.h>
|
||||||
#include <stasis/logger/logger2.h>
|
#include <stasis/logger/logger2.h>
|
||||||
#include <stasis/operations/alloc.h>
|
#include <stasis/operations/alloc.h>
|
||||||
|
|
||||||
void stasis_recovery_initiate(stasis_log_t* log, stasis_alloc_t * alloc);
|
void stasis_recovery_initiate(stasis_log_t* log, stasis_transaction_table_t * tbl, stasis_alloc_t * alloc);
|
||||||
/** This really doesn't belong in recovery.c, but there's so much code overlap, it doesn't make sense not to put it there. */
|
/** This really doesn't belong in recovery.c, but there's so much code overlap, it doesn't make sense not to put it there.
|
||||||
void undoTrans(stasis_log_t*log, TransactionLog transaction);
|
*
|
||||||
|
* XXX undoTrans should not take the entire transaction table as an argument. Instead, it should place its transaction argument directly into the list of transactions that undo processes.
|
||||||
|
* */
|
||||||
|
void undoTrans(stasis_log_t*log, stasis_transaction_table_t * tbl, stasis_transaction_table_entry_t transaction);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -9,31 +9,27 @@
|
||||||
#define TRANSACTIONTABLE_H_
|
#define TRANSACTIONTABLE_H_
|
||||||
|
|
||||||
#include <stasis/common.h>
|
#include <stasis/common.h>
|
||||||
typedef struct TransactionLog TransactionLog;
|
|
||||||
|
typedef struct stasis_transaction_table_entry_t stasis_transaction_table_entry_t;
|
||||||
|
typedef struct stasis_transaction_table_t stasis_transaction_table_t;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Contains the state needed by the logging layer to perform
|
Contains the state needed by the logging layer to perform
|
||||||
operations on a transaction.
|
operations on a transaction.
|
||||||
*/
|
*/
|
||||||
struct TransactionLog {
|
struct stasis_transaction_table_entry_t {
|
||||||
int xid;
|
int xid;
|
||||||
lsn_t prevLSN;
|
lsn_t prevLSN;
|
||||||
lsn_t recLSN;
|
lsn_t recLSN;
|
||||||
pthread_mutex_t mut;
|
pthread_mutex_t mut;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
|
||||||
XXX TransactionTable should be private to transactional2.c!
|
|
||||||
*/
|
|
||||||
extern TransactionLog stasis_transaction_table[MAX_TRANSACTIONS];
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Initialize Stasis' transaction table. Called by Tinit() and unit
|
Initialize Stasis' transaction table. Called by Tinit() and unit
|
||||||
tests that wish to test portions of Stasis in isolation.
|
tests that wish to test portions of Stasis in isolation.
|
||||||
*/
|
*/
|
||||||
void stasis_transaction_table_init();
|
stasis_transaction_table_t* stasis_transaction_table_init();
|
||||||
/** Free resources associated with the transaction table */
|
/** Free resources associated with the transaction table */
|
||||||
void stasis_transaction_table_deinit();
|
void stasis_transaction_table_deinit(stasis_transaction_table_t*);
|
||||||
/**
|
/**
|
||||||
* Used by recovery to prevent reuse of old transaction ids.
|
* Used by recovery to prevent reuse of old transaction ids.
|
||||||
*
|
*
|
||||||
|
@ -41,33 +37,34 @@ void stasis_transaction_table_deinit();
|
||||||
*
|
*
|
||||||
* @param xid The highest transaction id issued so far.
|
* @param xid The highest transaction id issued so far.
|
||||||
*/
|
*/
|
||||||
void stasis_transaction_table_max_transaction_id_set(int xid);
|
void stasis_transaction_table_max_transaction_id_set(stasis_transaction_table_t*,int xid);
|
||||||
/**
|
/**
|
||||||
* Used by test cases to mess with internal transaction table state.
|
* Used by test cases to mess with internal transaction table state.
|
||||||
*
|
*
|
||||||
* @param xid The new active transaction count.
|
* @param xid The new active transaction count.
|
||||||
*/
|
*/
|
||||||
void stasis_transaction_table_active_transaction_count_set(int xid);
|
void stasis_transaction_table_active_transaction_count_set(stasis_transaction_table_t*,int xid);
|
||||||
|
|
||||||
int stasis_transaction_table_roll_forward(int xid, lsn_t lsn, lsn_t prevLSN);
|
int stasis_transaction_table_roll_forward(stasis_transaction_table_t*,int xid, lsn_t lsn, lsn_t prevLSN);
|
||||||
/**
|
/**
|
||||||
@todo update Tprepare() to not write reclsn to log, then remove
|
@todo update Tprepare() to not write reclsn to log, then remove
|
||||||
this function.
|
this function.
|
||||||
*/
|
*/
|
||||||
int stasis_transaction_table_roll_forward_with_reclsn(int xid, lsn_t lsn,
|
int stasis_transaction_table_roll_forward_with_reclsn(stasis_transaction_table_t*,int xid, lsn_t lsn,
|
||||||
lsn_t prevLSN,
|
lsn_t prevLSN,
|
||||||
lsn_t recLSN);
|
lsn_t recLSN);
|
||||||
/**
|
/**
|
||||||
This is used by log truncation.
|
This is used by log truncation.
|
||||||
*/
|
*/
|
||||||
lsn_t stasis_transaction_table_minRecLSN();
|
lsn_t stasis_transaction_table_minRecLSN(stasis_transaction_table_t*);
|
||||||
|
|
||||||
TransactionLog * stasis_transaction_table_begin(int * xid);
|
stasis_transaction_table_entry_t * stasis_transaction_table_begin(stasis_transaction_table_t*,int * xid);
|
||||||
TransactionLog * stasis_transaction_table_get(int xid);
|
stasis_transaction_table_entry_t * stasis_transaction_table_get(stasis_transaction_table_t*,int xid);
|
||||||
int stasis_transaction_table_commit(int xid);
|
int stasis_transaction_table_commit(stasis_transaction_table_t*,int xid);
|
||||||
int stasis_transaction_table_forget(int xid);
|
int stasis_transaction_table_forget(stasis_transaction_table_t*,int xid);
|
||||||
|
|
||||||
int stasis_transaction_table_num_active();
|
int stasis_transaction_table_num_active(stasis_transaction_table_t*);
|
||||||
int* stasis_transaction_table_list_active();
|
int* stasis_transaction_table_list_active(stasis_transaction_table_t*);
|
||||||
|
int stasis_transaction_table_is_active(stasis_transaction_table_t*, int xid);
|
||||||
|
|
||||||
#endif /* TRANSACTIONTABLE_H_ */
|
#endif /* TRANSACTIONTABLE_H_ */
|
||||||
|
|
|
@ -774,6 +774,8 @@ void * stasis_log(void);
|
||||||
*/
|
*/
|
||||||
void * stasis_runtime_dirty_page_table();
|
void * stasis_runtime_dirty_page_table();
|
||||||
|
|
||||||
|
void * stasis_runtime_transaction_table();
|
||||||
|
|
||||||
void * stasis_runtime_alloc_state();
|
void * stasis_runtime_alloc_state();
|
||||||
|
|
||||||
void * stasis_runtime_buffer_manager();
|
void * stasis_runtime_buffer_manager();
|
||||||
|
|
|
@ -63,9 +63,11 @@ typedef struct stasis_truncation_t stasis_truncation_t;
|
||||||
|
|
||||||
#include <stasis/logger/logger2.h>
|
#include <stasis/logger/logger2.h>
|
||||||
#include <stasis/dirtyPageTable.h>
|
#include <stasis/dirtyPageTable.h>
|
||||||
|
#include <stasis/transactionTable.h>
|
||||||
#include <stasis/bufferManager.h>
|
#include <stasis/bufferManager.h>
|
||||||
|
|
||||||
stasis_truncation_t * stasis_truncation_init(stasis_dirty_page_table_t * dpt, stasis_buffer_manager_t * bufferManager, stasis_log_t * log);
|
stasis_truncation_t * stasis_truncation_init(stasis_dirty_page_table_t * dpt, stasis_transaction_table_t * tbl,
|
||||||
|
stasis_buffer_manager_t * bufferManager, stasis_log_t * log);
|
||||||
void stasis_truncation_deinit(stasis_truncation_t * trunc);
|
void stasis_truncation_deinit(stasis_truncation_t * trunc);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -427,7 +427,7 @@ void reopenLogWorkload(int truncating) {
|
||||||
const int SYNC_POINT = 900;
|
const int SYNC_POINT = 900;
|
||||||
stasis_log_t * stasis_log_file = 0;
|
stasis_log_t * stasis_log_file = 0;
|
||||||
|
|
||||||
stasis_transaction_table_active_transaction_count_set(0);
|
stasis_transaction_table_active_transaction_count_set(stasis_runtime_transaction_table(), 0);
|
||||||
|
|
||||||
if(LOG_TO_FILE == stasis_log_type) {
|
if(LOG_TO_FILE == stasis_log_type) {
|
||||||
stasis_log_file = stasis_log_safe_writes_open(stasis_log_file_name,
|
stasis_log_file = stasis_log_safe_writes_open(stasis_log_file_name,
|
||||||
|
@ -441,7 +441,7 @@ void reopenLogWorkload(int truncating) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int xid = 1;
|
int xid = 1;
|
||||||
TransactionLog l;
|
stasis_transaction_table_entry_t l;
|
||||||
pthread_mutex_init(&l.mut,0);
|
pthread_mutex_init(&l.mut,0);
|
||||||
stasis_log_begin_transaction(stasis_log_file, xid, &l);
|
stasis_log_begin_transaction(stasis_log_file, xid, &l);
|
||||||
lsn_t startLSN = 0;
|
lsn_t startLSN = 0;
|
||||||
|
|
|
@ -642,7 +642,7 @@ START_TEST(operation_reorderable) {
|
||||||
|
|
||||||
stasis_log_reordering_handle_t * rh
|
stasis_log_reordering_handle_t * rh
|
||||||
= stasis_log_reordering_handle_open(
|
= stasis_log_reordering_handle_open(
|
||||||
&stasis_transaction_table[xid[0]% MAX_TRANSACTIONS],
|
stasis_transaction_table_get(stasis_runtime_transaction_table(), xid[0]),
|
||||||
stasis_log(),
|
stasis_log(),
|
||||||
100, // bytes (far too low!)
|
100, // bytes (far too low!)
|
||||||
10, // log entries
|
10, // log entries
|
||||||
|
|
Loading…
Reference in a new issue