void MET_set_capabilities(ISC_STATUS* user_status, tdr* trans) { AliceGlobals* tdgbl = AliceGlobals::getSpecific(); if (!(DB = trans->tdr_db_handle)) return; /*START_TRANSACTION*/ { { isc_start_transaction (isc_status, (FB_API_HANDLE*) &gds_trans, (short) 1, &DB, (short) 0, (char*) 0); }; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } trans->tdr_db_caps = get_capabilities(user_status); /*ROLLBACK*/ { isc_rollback_transaction (isc_status, (FB_API_HANDLE*) &gds_trans);; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } }
/* ** Closes a connection. ** Lua Returns: ** 1 if close was sucsessful, 0 if already closed ** nil and error message otherwise. */ static int conn_close (lua_State *L) { conn_data *conn = (conn_data *)luaL_checkudata(L,1,LUASQL_CONNECTION_FIREBIRD); luaL_argcheck (L, conn != NULL, 1, "connection expected"); /* already closed */ if(conn->closed != 0) { lua_pushboolean(L, 0); return 1; } /* are all related cursors closed? */ if(conn->lock > 0) return luasql_faildirect(L, "there are still open cursors"); if(conn->autocommit != 0) isc_commit_transaction(conn->env->status_vector, &conn->transaction); else isc_rollback_transaction(conn->env->status_vector, &conn->transaction); if ( CHECK_DB_ERROR(conn->env->status_vector) ) return return_db_error(L, conn->env->status_vector); isc_detach_database(conn->env->status_vector, &conn->db); if ( CHECK_DB_ERROR(conn->env->status_vector) ) return return_db_error(L, conn->env->status_vector); conn->closed = 1; --conn->env->lock; /* check environment can be GC'd */ if(conn->env->lock == 0) lua_unregisterobj(L, conn->env); lua_pushboolean(L, 1); return 1; }
static void _php_ibase_free_trans(zend_resource *rsrc) /* {{{ */ { ibase_trans *trans = (ibase_trans *)rsrc->ptr; unsigned short i; IBDEBUG("Cleaning up transaction resource..."); if (trans->handle != 0) { IBDEBUG("Rolling back unhandled transaction..."); if (isc_rollback_transaction(IB_STATUS, &trans->handle)) { _php_ibase_error(); } } /* now remove this transaction from all the connection-transaction lists */ for (i = 0; i < trans->link_cnt; ++i) { if (trans->db_link[i] != NULL) { ibase_tr_list **l; for (l = &trans->db_link[i]->tr_list; *l != NULL; l = &(*l)->next) { if ( (*l)->trans == trans) { ibase_tr_list *p = *l; *l = p->next; efree(p); break; } } } } efree(trans); }
/** * This function provides the rollback method for the Transaction class. * * @param self A reference to the Transaction object being rolled back. * * @return A reference to self if successful, nil otherwise. * */ static VALUE rollbackTransaction(VALUE self) { TransactionHandle *transaction = NULL; Data_Get_Struct(self, TransactionHandle, transaction); /* Roll back the transaction. */ if(transaction->handle != 0) { ISC_STATUS status[ISC_STATUS_LENGTH]; if(isc_rollback_transaction(status, &transaction->handle) != 0) { /* Generate an error. */ rb_fireruby_raise(status, "Error rolling back transaction."); } transaction->handle = 0; } else { /* Generate an error. */ rb_fireruby_raise(NULL, "2. Transaction is not active."); } /* Notify each connection of the transactions end. */ rb_tx_released(rb_iv_get(self, "@connections"), self); /* Clear the connections list. */ rb_iv_set(self, "@connections", rb_ary_new()); return(self); }
EXPORT RM_ENTRY(rmc_rollback_transaction) { ClearParamPool(); ISC_STATUS *stat = AllocStatusPool(); isc_rollback_transaction(stat, (isc_tr_handle *)arg_vector[1].a_address); StatusToCobol(&arg_vector[0], stat); return (0); }
int fb_rollback(rlm_sql_firebird_conn_t *conn) { conn->sql_code = 0; if (conn->trh) { isc_rollback_transaction(conn->status, &conn->trh); // conn->in_use = 0; pthread_mutex_unlock(&conn->mut); if (IS_ISC_ERROR(conn->status)) { return fb_error(conn); } } return conn->sql_code; }
static void _php_ibase_commit_link(ibase_db_link *link) /* {{{ */ { unsigned short i = 0, j; ibase_tr_list *l; ibase_event *e; IBDEBUG("Checking transactions to close..."); for (l = link->tr_list; l != NULL; ++i) { ibase_tr_list *p = l; if (p->trans != 0) { if (i == 0) { if (p->trans->handle != 0) { IBDEBUG("Committing default transaction..."); if (isc_commit_transaction(IB_STATUS, &p->trans->handle)) { _php_ibase_error(); } } efree(p->trans); /* default transaction is not a registered resource: clean up */ } else { if (p->trans->handle != 0) { /* non-default trans might have been rolled back by other call of this dtor */ IBDEBUG("Rolling back other transactions..."); if (isc_rollback_transaction(IB_STATUS, &p->trans->handle)) { _php_ibase_error(); } } /* set this link pointer to NULL in the transaction */ for (j = 0; j < p->trans->link_cnt; ++j) { if (p->trans->db_link[j] == link) { p->trans->db_link[j] = NULL; break; } } } } l = l->next; efree(p); } link->tr_list = NULL; for (e = link->event_head; e; e = e->event_next) { _php_ibase_free_event(e); e->link = NULL; } }
/* ** GCs an connection object */ static int conn_gc (lua_State *L) { conn_data *conn = (conn_data *)luaL_checkudata(L,1,LUASQL_CONNECTION_FIREBIRD); if(conn->closed == 0) { if(conn->autocommit != 0) isc_commit_transaction(conn->env->status_vector, &conn->transaction); else isc_rollback_transaction(conn->env->status_vector, &conn->transaction); isc_detach_database(conn->env->status_vector, &conn->db); conn->closed = 1; --conn->env->lock; /* check environment can be GC'd */ if(conn->env->lock == 0) lua_unregisterobj(L, conn->env); } return 0; }
tdr* MET_get_transaction(ISC_STATUS* user_status, isc_db_handle handle, SLONG id) { struct isc_9_struct { ISC_QUAD isc_10; /* RDB$TRANSACTION_DESCRIPTION */ short isc_11; /* isc_utility */ } isc_9; struct isc_7_struct { ISC_LONG isc_8; /* RDB$TRANSACTION_ID */ } isc_7; FB_API_HANDLE request = 0; tdr* trans = NULL; AliceGlobals* tdgbl = AliceGlobals::getSpecific(); if (!(DB = handle)) return 0; /*START_TRANSACTION*/ { { isc_start_transaction (isc_status, (FB_API_HANDLE*) &gds_trans, (short) 1, &DB, (short) 0, (char*) 0); }; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } const USHORT capabilities = get_capabilities(user_status); if (capabilities & CAP_transactions) { /*FOR(REQUEST_HANDLE request) TRA IN RDB$TRANSACTIONS WITH TRA.RDB$TRANSACTION_ID = id AND TRA.RDB$TRANSACTION_DESCRIPTION NOT MISSING*/ { if (!request) isc_compile_request (isc_status, (FB_API_HANDLE*) &DB, (FB_API_HANDLE*) &request, (short) sizeof(isc_6), (char*) isc_6); isc_7.isc_8 = id; if (request) isc_start_and_send (isc_status, (FB_API_HANDLE*) &request, (FB_API_HANDLE*) &gds_trans, (short) 0, (short) 4, &isc_7, (short) 0); if (!isc_status [1]) { while (1) { isc_receive (isc_status, (FB_API_HANDLE*) &request, (short) 1, (short) 10, &isc_9, (short) 0); if (!isc_9.isc_11 || isc_status [1]) break; trans = get_description(&/*TRA.RDB$TRANSACTION_DESCRIPTION*/ isc_9.isc_10); /*END_FOR*/ } }; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } isc_release_request(gds_status, &request); if (gds_status[1]) { return_error(user_status); } } /*ROLLBACK*/ { isc_rollback_transaction (isc_status, (FB_API_HANDLE*) &gds_trans);; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } if (trans) trans->tdr_db_caps = capabilities; return trans; }
void MET_get_state(ISC_STATUS* user_status, tdr* trans) { struct isc_15_struct { short isc_16; /* isc_utility */ short isc_17; /* RDB$TRANSACTION_STATE */ } isc_15; struct isc_13_struct { ISC_LONG isc_14; /* RDB$TRANSACTION_ID */ } isc_13; FB_API_HANDLE request = 0; AliceGlobals* tdgbl = AliceGlobals::getSpecific(); if (!(DB = trans->tdr_db_handle) || !(trans->tdr_db_caps & CAP_transactions)) { trans->tdr_state = TRA_unknown; return; } /*START_TRANSACTION*/ { { isc_start_transaction (isc_status, (FB_API_HANDLE*) &gds_trans, (short) 1, &DB, (short) 0, (char*) 0); }; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } /*FOR(REQUEST_HANDLE request) TRA IN RDB$TRANSACTIONS WITH TRA.RDB$TRANSACTION_ID = trans->tdr_id*/ { if (!request) isc_compile_request (isc_status, (FB_API_HANDLE*) &DB, (FB_API_HANDLE*) &request, (short) sizeof(isc_12), (char*) isc_12); isc_13.isc_14 = trans->tdr_id; if (request) isc_start_and_send (isc_status, (FB_API_HANDLE*) &request, (FB_API_HANDLE*) &gds_trans, (short) 0, (short) 4, &isc_13, (short) 0); if (!isc_status [1]) { while (1) { isc_receive (isc_status, (FB_API_HANDLE*) &request, (short) 1, (short) 4, &isc_15, (short) 0); if (!isc_15.isc_16 || isc_status [1]) break; trans->tdr_state = /*TRA.RDB$TRANSACTION_STATE*/ isc_15.isc_17; /*END_FOR*/ } }; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } isc_release_request(gds_status, &request); if (gds_status[1]) { return_error(user_status); } /*ROLLBACK*/ { isc_rollback_transaction (isc_status, (FB_API_HANDLE*) &gds_trans);; /*ON_ERROR*/ if (isc_status [1]) { return_error(user_status); /*END_ERROR;*/ } } }
int main (int argc, char** argv) { char dept_no[4]; double percent_inc; short flag0 = 0, flag1 = 0; XSQLDA *sqlda; long sqlcode; char empdb[128]; if (argc > 1) strcpy(empdb, argv[1]); else strcpy(empdb, "employee.fdb"); if (isc_attach_database(status, 0, empdb, &DB, 0, NULL)) { ERREXIT(status, 1) } /* Allocate an input SQLDA. There are two unknown parameters. */ sqlda = (XSQLDA *) malloc(XSQLDA_LENGTH(2)); sqlda->sqln = 2; sqlda->sqld = 2; sqlda->version = 1; sqlda->sqlvar[0].sqldata = (char *) &percent_inc; sqlda->sqlvar[0].sqltype = SQL_DOUBLE + 1; sqlda->sqlvar[0].sqllen = sizeof(percent_inc); sqlda->sqlvar[0].sqlind = &flag0; flag0 = 0; sqlda->sqlvar[1].sqldata = dept_no; sqlda->sqlvar[1].sqltype = SQL_TEXT + 1; sqlda->sqlvar[1].sqllen = 3; sqlda->sqlvar[1].sqlind = &flag1; flag1 = 0; /* * Get the next department-percent increase input pair. */ while (get_input(dept_no, &percent_inc)) { printf("\nIncreasing budget for department: %s by %5.2lf percent.\n", dept_no, percent_inc); if (isc_start_transaction(status, &trans, 1, &DB, 0, NULL)) { ERREXIT(status, 1) } /* Update the budget. */ isc_dsql_execute_immediate(status, &DB, &trans, 0, updstr, 1, sqlda); sqlcode = isc_sqlcode(status); if (sqlcode) { /* Don't save the update, if the new budget exceeds the limit. */ if (sqlcode == -625) { printf("\tExceeded budget limit -- not updated.\n"); if (isc_rollback_transaction(status, &trans)) { ERREXIT(status, 1) } continue; } /* Undo all changes, in case of an error. */ else { isc_print_status(status); printf("SQLCODE=%d\n", sqlcode); isc_rollback_transaction(status, &trans); ERREXIT(status, 1) } }
ISC_STATUS API_ROUTINE gds__rollback_transaction(ISC_STATUS * status_vector, FB_API_HANDLE* tra_handle) { return isc_rollback_transaction(status_vector, tra_handle); }