Commit e4daae90 authored by unknown's avatar unknown

Merge joreland@bk-internal.mysql.com:/home/bk/mysql-5.0

into mysql.com:/home/jonas/src/mysql-5.0


sql/sql_parse.cc:
  Auto merged
parents 736f9b4b c398f5cc
......@@ -32,7 +32,8 @@ testTransactions \
testDeadlock \
test_event ndbapi_slow_select testReadPerf testLcp \
testPartitioning \
testBitfield
testBitfield \
DbCreate DbAsyncGenerator
#flexTimedAsynch
#testBlobs
......@@ -73,6 +74,8 @@ testReadPerf_SOURCES = testReadPerf.cpp
testLcp_SOURCES = testLcp.cpp
testPartitioning_SOURCES = testPartitioning.cpp
testBitfield_SOURCES = testBitfield.cpp
DbCreate_SOURCES= bench/mainPopulate.cpp bench/dbPopulate.cpp bench/userInterface.cpp
DbAsyncGenerator_SOURCES= bench/mainAsyncGenerator.cpp bench/asyncGenerator.cpp bench/ndb_async2.cpp
INCLUDES_LOC = -I$(top_srcdir)/ndb/include/kernel
......
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include <ndb_global.h>
#include "dbGenerator.h"
#include <NdbApi.hpp>
#include <NdbOut.hpp>
#include <NdbSleep.h>
/***************************************************************
* L O C A L C O N S T A N T S *
***************************************************************/
/***************************************************************
* L O C A L D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* L O C A L F U N C T I O N S *
***************************************************************/
static void getRandomSubscriberNumber(SubscriberNumber number);
static void getRandomServerId(ServerId *serverId);
static void getRandomChangedBy(ChangedBy changedBy);
static void getRandomChangedTime(ChangedTime changedTime);
static void clearTransaction(TransactionDefinition *trans);
static void initGeneratorStatistics(GeneratorStatistics *gen);
static void doOneTransaction(ThreadData * td,
int parallellism,
int millisSendPoll,
int minEventSendPoll,
int forceSendPoll);
static void doTransaction_T1(Ndb * pNDB, ThreadData * td, int async);
static void doTransaction_T2(Ndb * pNDB, ThreadData * td, int async);
static void doTransaction_T3(Ndb * pNDB, ThreadData * td, int async);
static void doTransaction_T4(Ndb * pNDB, ThreadData * td, int async);
static void doTransaction_T5(Ndb * pNDB, ThreadData * td, int async);
/***************************************************************
* L O C A L D A T A *
***************************************************************/
static SequenceValues transactionDefinition[] = {
{25, 1},
{25, 2},
{20, 3},
{15, 4},
{15, 5},
{0, 0}
};
static SequenceValues rollbackDefinition[] = {
{98, 0},
{2 , 1},
{0, 0}
};
static int maxsize = 0;
/***************************************************************
* P U B L I C D A T A *
***************************************************************/
/***************************************************************
****************************************************************
* L O C A L F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
static void getRandomSubscriberNumber(SubscriberNumber number)
{
uint32 tmp;
char sbuf[SUBSCRIBER_NUMBER_LENGTH + 1];
tmp = myRandom48(NO_OF_SUBSCRIBERS);
sprintf(sbuf, "%.*d", SUBSCRIBER_NUMBER_LENGTH, tmp);
memcpy(number, sbuf, SUBSCRIBER_NUMBER_LENGTH);
}
static void getRandomServerId(ServerId *serverId)
{
*serverId = myRandom48(NO_OF_SERVERS);
}
static void getRandomChangedBy(ChangedBy changedBy)
{
memset(changedBy, myRandom48(26)+'A', CHANGED_BY_LENGTH);
changedBy[CHANGED_BY_LENGTH] = 0;
}
static void getRandomChangedTime(ChangedTime changedTime)
{
memset(changedTime, myRandom48(26)+'A', CHANGED_TIME_LENGTH);
changedTime[CHANGED_TIME_LENGTH] = 0;
}
static void clearTransaction(TransactionDefinition *trans)
{
trans->count = 0;
trans->branchExecuted = 0;
trans->rollbackExecuted = 0;
trans->latencyCounter = myRandom48(127);
trans->latency.reset();
}
static int listFull(SessionList *list)
{
return(list->numberInList == SESSION_LIST_LENGTH);
}
static int listEmpty(SessionList *list)
{
return(list->numberInList == 0);
}
static void insertSession(SessionList *list,
SubscriberNumber number,
ServerId serverId)
{
SessionElement *e;
if( listFull(list) ) return;
e = &list->list[list->writeIndex];
strcpy(e->subscriberNumber, number);
e->serverId = serverId;
list->writeIndex = (list->writeIndex + 1) % SESSION_LIST_LENGTH;
list->numberInList++;
if( list->numberInList > maxsize )
maxsize = list->numberInList;
}
static SessionElement *getNextSession(SessionList *list)
{
if( listEmpty(list) ) return(0);
return(&list->list[list->readIndex]);
}
static void deleteSession(SessionList *list)
{
if( listEmpty(list) ) return;
list->readIndex = (list->readIndex + 1) % SESSION_LIST_LENGTH;
list->numberInList--;
}
static void initGeneratorStatistics(GeneratorStatistics *gen)
{
int i;
if( initSequence(&gen->transactionSequence,
transactionDefinition) != 0 ) {
ndbout_c("could not set the transaction types");
exit(0);
}
if( initSequence(&gen->rollbackSequenceT4,
rollbackDefinition) != 0 ) {
ndbout_c("could not set the rollback sequence");
exit(0);
}
if( initSequence(&gen->rollbackSequenceT5,
rollbackDefinition) != 0 ) {
ndbout_c("could not set the rollback sequence");
exit(0);
}
for(i = 0; i < NUM_TRANSACTION_TYPES; i++ )
clearTransaction(&gen->transactions[i]);
gen->totalTransactions = 0;
gen->activeSessions.numberInList = 0;
gen->activeSessions.readIndex = 0;
gen->activeSessions.writeIndex = 0;
}
static
void
doOneTransaction(ThreadData * td, int p, int millis, int minEvents, int force)
{
int i;
unsigned int transactionType;
int async = 1;
if (p == 1) {
async = 0;
}//if
for(i = 0; i<p; i++){
if(td[i].runState == Runnable){
transactionType = getNextRandom(&td[i].generator.transactionSequence);
switch(transactionType) {
case 1:
doTransaction_T1(td[i].pNDB, &td[i], async);
break;
case 2:
doTransaction_T2(td[i].pNDB, &td[i], async);
break;
case 3:
doTransaction_T3(td[i].pNDB, &td[i], async);
break;
case 4:
doTransaction_T4(td[i].pNDB, &td[i], async);
break;
case 5:
doTransaction_T5(td[i].pNDB, &td[i], async);
break;
default:
ndbout_c("Unknown transaction type: %d", transactionType);
}
}
}
if (async == 1) {
td[0].pNDB->sendPollNdb(millis, minEvents, force);
}//if
}
static
void
doTransaction_T1(Ndb * pNDB, ThreadData * td, int async)
{
/*----------------*/
/* Init arguments */
/*----------------*/
getRandomSubscriberNumber(td->transactionData.number);
getRandomChangedBy(td->transactionData.changed_by);
BaseString::snprintf(td->transactionData.changed_time,
sizeof(td->transactionData.changed_time),
"%ld - %d", td->changedTime++, myRandom48(65536*1024));
//getRandomChangedTime(td->transactionData.changed_time);
td->transactionData.location = td->transactionData.changed_by[0];
/*-----------------*/
/* Run transaction */
/*-----------------*/
td->runState = Running;
td->generator.transactions[0].startLatency();
start_T1(pNDB, td, async);
}
static
void
doTransaction_T2(Ndb * pNDB, ThreadData * td, int async)
{
/*----------------*/
/* Init arguments */
/*----------------*/
getRandomSubscriberNumber(td->transactionData.number);
/*-----------------*/
/* Run transaction */
/*-----------------*/
td->runState = Running;
td->generator.transactions[1].startLatency();
start_T2(pNDB, td, async);
}
static
void
doTransaction_T3(Ndb * pNDB, ThreadData * td, int async)
{
SessionElement *se;
/*----------------*/
/* Init arguments */
/*----------------*/
se = getNextSession(&td->generator.activeSessions);
if( se ) {
strcpy(td->transactionData.number, se->subscriberNumber);
td->transactionData.server_id = se->serverId;
td->transactionData.sessionElement = 1;
} else {
getRandomSubscriberNumber(td->transactionData.number);
getRandomServerId(&td->transactionData.server_id);
td->transactionData.sessionElement = 0;
}
td->transactionData.server_bit = (1 << td->transactionData.server_id);
/*-----------------*/
/* Run transaction */
/*-----------------*/
td->runState = Running;
td->generator.transactions[2].startLatency();
start_T3(pNDB, td, async);
}
static
void
doTransaction_T4(Ndb * pNDB, ThreadData * td, int async)
{
/*----------------*/
/* Init arguments */
/*----------------*/
getRandomSubscriberNumber(td->transactionData.number);
getRandomServerId(&td->transactionData.server_id);
td->transactionData.server_bit = (1 << td->transactionData.server_id);
td->transactionData.do_rollback =
getNextRandom(&td->generator.rollbackSequenceT4);
#if 0
memset(td->transactionData.session_details,
myRandom48(26)+'A', SESSION_DETAILS_LENGTH);
#endif
td->transactionData.session_details[SESSION_DETAILS_LENGTH] = 0;
/*-----------------*/
/* Run transaction */
/*-----------------*/
td->runState = Running;
td->generator.transactions[3].startLatency();
start_T4(pNDB, td, async);
}
static
void
doTransaction_T5(Ndb * pNDB, ThreadData * td, int async)
{
SessionElement * se;
se = getNextSession(&td->generator.activeSessions);
if( se ) {
strcpy(td->transactionData.number, se->subscriberNumber);
td->transactionData.server_id = se->serverId;
td->transactionData.sessionElement = 1;
}
else {
getRandomSubscriberNumber(td->transactionData.number);
getRandomServerId(&td->transactionData.server_id);
td->transactionData.sessionElement = 0;
}
td->transactionData.server_bit = (1 << td->transactionData.server_id);
td->transactionData.do_rollback
= getNextRandom(&td->generator.rollbackSequenceT5);
/*-----------------*/
/* Run transaction */
/*-----------------*/
td->runState = Running;
td->generator.transactions[4].startLatency();
start_T5(pNDB, td, async);
}
void
complete_T1(ThreadData * data){
data->generator.transactions[0].stopLatency();
data->generator.transactions[0].count++;
data->runState = Runnable;
data->generator.totalTransactions++;
}
void
complete_T2(ThreadData * data){
data->generator.transactions[1].stopLatency();
data->generator.transactions[1].count++;
data->runState = Runnable;
data->generator.totalTransactions++;
}
void
complete_T3(ThreadData * data){
data->generator.transactions[2].stopLatency();
data->generator.transactions[2].count++;
if(data->transactionData.branchExecuted)
data->generator.transactions[2].branchExecuted++;
data->runState = Runnable;
data->generator.totalTransactions++;
}
void
complete_T4(ThreadData * data){
data->generator.transactions[3].stopLatency();
data->generator.transactions[3].count++;
if(data->transactionData.branchExecuted)
data->generator.transactions[3].branchExecuted++;
if(data->transactionData.do_rollback)
data->generator.transactions[3].rollbackExecuted++;
if(data->transactionData.branchExecuted &&
!data->transactionData.do_rollback){
insertSession(&data->generator.activeSessions,
data->transactionData.number,
data->transactionData.server_id);
}
data->runState = Runnable;
data->generator.totalTransactions++;
}
void
complete_T5(ThreadData * data){
data->generator.transactions[4].stopLatency();
data->generator.transactions[4].count++;
if(data->transactionData.branchExecuted)
data->generator.transactions[4].branchExecuted++;
if(data->transactionData.do_rollback)
data->generator.transactions[4].rollbackExecuted++;
if(data->transactionData.sessionElement &&
!data->transactionData.do_rollback){
deleteSession(&data->generator.activeSessions);
}
data->runState = Runnable;
data->generator.totalTransactions++;
}
/***************************************************************
****************************************************************
* P U B L I C F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
void
asyncGenerator(ThreadData *data,
int parallellism,
int millisSendPoll,
int minEventSendPoll,
int forceSendPoll)
{
ThreadData * startUp;
GeneratorStatistics *st;
double periodStop;
double benchTimeStart;
double benchTimeEnd;
int i, j, done;
myRandom48Init(data->randomSeed);
for(i = 0; i<parallellism; i++){
initGeneratorStatistics(&data[i].generator);
}
startUp = (ThreadData*)malloc(parallellism * sizeof(ThreadData));
memcpy(startUp, data, (parallellism * sizeof(ThreadData)));
/*----------------*/
/* warm up period */
/*----------------*/
periodStop = userGetTime() + (double)data[0].warmUpSeconds;
while(userGetTime() < periodStop){
doOneTransaction(startUp, parallellism,
millisSendPoll, minEventSendPoll, forceSendPoll);
}
ndbout_c("Waiting for startup to finish");
/**
* Wait for all transactions
*/
done = 0;
while(!done){
done = 1;
for(i = 0; i<parallellism; i++){
if(startUp[i].runState != Runnable){
done = 0;
break;
}
}
if(!done){
startUp[0].pNDB->sendPollNdb();
}
}
ndbout_c("Benchmark period starts");
/*-------------------------*/
/* normal benchmark period */
/*-------------------------*/
benchTimeStart = userGetTime();
periodStop = benchTimeStart + (double)data[0].testSeconds;
while(userGetTime() < periodStop)
doOneTransaction(data, parallellism,
millisSendPoll, minEventSendPoll, forceSendPoll);
benchTimeEnd = userGetTime();
ndbout_c("Benchmark period done");
/**
* Wait for all transactions
*/
done = 0;
while(!done){
done = 1;
for(i = 0; i<parallellism; i++){
if(data[i].runState != Runnable){
done = 0;
break;
}
}
if(!done){
data[0].pNDB->sendPollNdb();
}
}
/*------------------*/
/* cool down period */
/*------------------*/
periodStop = userGetTime() + (double)data[0].coolDownSeconds;
while(userGetTime() < periodStop){
doOneTransaction(startUp, parallellism,
millisSendPoll, minEventSendPoll, forceSendPoll);
}
done = 0;
while(!done){
done = 1;
for(i = 0; i<parallellism; i++){
if(startUp[i].runState != Runnable){
done = 0;
break;
}
}
if(!done){
startUp[0].pNDB->sendPollNdb();
}
}
/*---------------------------------------------------------*/
/* add the times for all transaction for inner loop timing */
/*---------------------------------------------------------*/
for(j = 0; j<parallellism; j++){
st = &data[j].generator;
st->outerLoopTime = benchTimeEnd - benchTimeStart;
st->outerTps = getTps(st->totalTransactions, st->outerLoopTime);
}
/* ndbout_c("maxsize = %d\n",maxsize); */
free(startUp);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef DBGENERATOR_H
#define DBGENERATOR_H
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include "testData.h"
#include "userInterface.h"
/***************************************************************
* M A C R O S *
***************************************************************/
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
#ifdef __cplusplus
extern "C" {
#endif
extern void asyncGenerator(ThreadData *d, int parallellism,
int millisSendPoll,
int minEventSendPoll,
int forceSendPoll);
#ifdef __cplusplus
}
#endif
/***************************************************************
* E X T E R N A L D A T A *
***************************************************************/
#endif /* DBGENERATOR_H */
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include <ndb_global.h>
#include "userInterface.h"
#include "dbPopulate.h"
#include <NdbOut.hpp>
#include <random.h>
/***************************************************************
* L O C A L C O N S T A N T S *
***************************************************************/
/***************************************************************
* L O C A L D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* L O C A L F U N C T I O N S *
***************************************************************/
static void getRandomSubscriberData(int subscriberNo,
SubscriberNumber number,
SubscriberName name);
static void populate(char *title,
int count,
void (*func)(UserHandle*,int),
UserHandle *uh);
static void populateServers(UserHandle *uh, int count);
static void populateSubscribers(UserHandle *uh, int count);
static void populateGroups(UserHandle *uh, int count);
/***************************************************************
* L O C A L D A T A *
***************************************************************/
static SequenceValues permissionsDefinition[] = {
{90, 1},
{10, 0},
{0, 0}
};
/***************************************************************
* P U B L I C D A T A *
***************************************************************/
/***************************************************************
****************************************************************
* L O C A L F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
static void getRandomSubscriberData(int subscriberNo,
SubscriberNumber number,
SubscriberName name)
{
char sbuf[SUBSCRIBER_NUMBER_LENGTH + 1];
sprintf(sbuf, "%.*d", SUBSCRIBER_NUMBER_LENGTH, subscriberNo);
memcpy(number, sbuf, SUBSCRIBER_NUMBER_LENGTH);
memset(name, myRandom48(26)+'A', SUBSCRIBER_NAME_LENGTH);
}
static void populate(char *title,
int count,
void (*func)(UserHandle*, int),
UserHandle *uh)
{
ndbout_c("Populating %d '%s' ... ",count, title);
/* fflush(stdout); */
func(uh,count);
ndbout_c("done");
}
static void populateServers(UserHandle *uh, int count)
{
int i, j;
int len;
char tmp[80];
int suffix_length = 1;
ServerName serverName;
SubscriberSuffix suffix;
int commitCount = 0;
for(i = 0; i < SUBSCRIBER_NUMBER_SUFFIX_LENGTH; i++)
suffix_length *= 10;
for(i = 0; i < count; i++) {
sprintf(tmp, "-Server %d-", i);
len = strlen(tmp);
for(j = 0; j < SERVER_NAME_LENGTH; j++){
serverName[j] = tmp[j % len];
}
/* serverName[j] = 0; not null-terminated */
for(j = 0; j < suffix_length; j++){
char sbuf[SUBSCRIBER_NUMBER_SUFFIX_LENGTH + 1];
sprintf(sbuf, "%.*d", SUBSCRIBER_NUMBER_SUFFIX_LENGTH, j);
memcpy(suffix, sbuf, SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
userDbInsertServer(uh, i, suffix, serverName);
commitCount ++;
if((commitCount % OP_PER_TRANS) == 0)
userDbCommit(uh);
}
}
if((commitCount % OP_PER_TRANS) != 0)
userDbCommit(uh);
}
static void populateSubscribers(UserHandle *uh, int count)
{
SubscriberNumber number;
SubscriberName name;
int i, j, k;
int res;
SequenceValues values[NO_OF_GROUPS+1];
RandomSequence seq;
for(i = 0; i < NO_OF_GROUPS; i++) {
values[i].length = 1;
values[i].value = i;
}
values[i].length = 0;
values[i].value = 0;
if( initSequence(&seq, values) != 0 ) {
ndbout_c("could not set the sequence of random groups");
exit(0);
}
#define RETRIES 25
for(i = 0; i < count; i+= OP_PER_TRANS) {
for(j = 0; j<RETRIES; j++){
for(k = 0; k<OP_PER_TRANS && i+k < count; k++){
getRandomSubscriberData(i+k, number, name);
userDbInsertSubscriber(uh, number, getNextRandom(&seq), name);
}
res = userDbCommit(uh);
if(res == 0)
break;
if(res != 1){
ndbout_c("Terminating");
exit(0);
}
}
if(j == RETRIES){
ndbout_c("Terminating");
exit(0);
}
}
}
static void populateGroups(UserHandle *uh, int count)
{
int i;
int j;
int len;
RandomSequence seq;
Permission allow[NO_OF_GROUPS];
ServerBit serverBit;
GroupName groupName;
char tmp[80];
int commitCount = 0;
if( initSequence(&seq, permissionsDefinition) != 0 ) {
ndbout_c("could not set the sequence of random permissions");
exit(0);
}
for(i = 0; i < NO_OF_GROUPS; i++)
allow[i] = 0;
for(i = 0; i < NO_OF_SERVERS; i++) {
serverBit = 1 << i;
for(j = 0; j < NO_OF_GROUPS; j++ ) {
if( getNextRandom(&seq) )
allow[j] |= serverBit;
}
}
for(i = 0; i < NO_OF_GROUPS; i++) {
sprintf(tmp, "-Group %d-", i);
len = strlen(tmp);
for(j = 0; j < GROUP_NAME_LENGTH; j++) {
groupName[j] = tmp[j % len];
}
/* groupName[j] = 0; not null-terminated */
userDbInsertGroup(uh,
i,
groupName,
allow[i],
allow[i],
allow[i]);
commitCount ++;
if((commitCount % OP_PER_TRANS) == 0)
userDbCommit(uh);
}
if((commitCount % OP_PER_TRANS) != 0)
userDbCommit(uh);
}
/***************************************************************
****************************************************************
* P U B L I C F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
void dbPopulate(UserHandle *uh)
{
populate("servers", NO_OF_SERVERS, populateServers, uh);
populate("subscribers", NO_OF_SUBSCRIBERS, populateSubscribers, uh);
populate("groups", NO_OF_GROUPS, populateGroups, uh);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef DBPOPULATE_H
#define DBPOPULATE_H
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include "userInterface.h"
/***************************************************************
* M A C R O S *
***************************************************************/
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
#ifdef __cplusplus
extern "C" {
#endif
extern void dbPopulate(UserHandle *uh);
#ifdef __cplusplus
}
#endif
/***************************************************************
* E X T E R N A L D A T A *
***************************************************************/
#endif /* DBPOPULATE_H */
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef MACROS_H
#define MACROS_H
#include <ndb_global.h>
#include <NdbOut.hpp>
#define ERROR(x) {ndbout_c((x));}
#define ERROR1(x,y) {ndbout_c((x), (y));}
#define ERROR2(x,y,z) {ndbout_c((x), (y), (z));}
#define ERROR3(x,y,z,u) {ndbout_c((x), (y), (z), (u));}
#define ERROR4(x,y,z,u,w) {ndbout_c((x), (y), (z), (u), (w));}
#define INIT_RANDOM(x) srand48((x))
#define UI_RANDOM(x) ((unsigned int)(lrand48()%(x)))
#define ASSERT(cond, message) \
{ if(!(cond)) { ERROR(message); exit(-1); }}
#ifdef DEBUG_ON
#define DEBUG(x) {ndbout_c((x));}
#define DEBUG1(x,y) {ndbout_c((x), (y));}
#define DEBUG2(x,y,z) {ndbout_c((x), (y), (z));}
#define DEBUG3(x,y,z,u) {ndbout_c((x), (y), (z), (u));}
#define DEBUG4(x,y,z,u,w) {ndbout_c((x), (y), (z), (u), (w));}
#define DEBUG5(x,y,z,u,w, v) {ndbout_c((x), (y), (z), (u), (w), (v));}
#else
#define DEBUG(x)
#define DEBUG1(x,y)
#define DEBUG2(x,y,z)
#define DEBUG3(x,y,z,u)
#define DEBUG4(x,y,z,u,w)
#define DEBUG5(x,y,z,u,w, v)
#endif
#endif
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#include <ndb_global.h>
#include <NdbHost.h>
#include <NdbSleep.h>
#include <NdbThread.h>
#include <NdbMain.h>
#include <NdbOut.hpp>
#include <NdbEnv.h>
#include <NdbTest.hpp>
#include "userInterface.h"
#include "dbGenerator.h"
static int numProcesses;
static int numSeconds;
static int numWarmSeconds;
static int parallellism;
static int millisSendPoll;
static int minEventSendPoll;
static int forceSendPoll;
static ThreadData *data;
static Ndb_cluster_connection *g_cluster_connection= 0;
static void usage(const char *prog)
{
const char *progname;
/*--------------------------------------------*/
/* Get the name of the program (without path) */
/*--------------------------------------------*/
progname = strrchr(prog, '/');
if (progname == 0)
progname = prog;
else
++progname;
ndbout_c(
"Usage: %s [-proc <num>] [-warm <num>] [-time <num>] [ -p <num>] "
"[-t <num> ] [ -e <num> ] [ -f <num>] \n"
" -proc <num> Specifies that <num> is the number of\n"
" threads. The default is 1.\n"
" -time <num> Specifies that the test will run for <num> sec.\n"
" The default is 10 sec\n"
" -warm <num> Specifies the warm-up/cooldown period of <num> "
"sec.\n"
" The default is 10 sec\n"
" -p <num> The no of parallell transactions started by "
"one thread\n"
" -e <num> Minimum no of events before wake up in call to "
"sendPoll\n"
" Default is 1\n"
" -f <num> force parameter to sendPoll\n"
" Default is 0\n",
progname);
}
static
int
parse_args(int argc, const char **argv)
{
int i;
numProcesses = 1;
numSeconds = 10;
numWarmSeconds = 10;
parallellism = 1;
millisSendPoll = 10000;
minEventSendPoll = 1;
forceSendPoll = 0;
i = 1;
while (i < argc){
if (strcmp("-proc",argv[i]) == 0) {
if (i + 1 >= argc) {
return 1;
}
if (sscanf(argv[i+1], "%d", &numProcesses) == -1 ||
numProcesses <= 0 || numProcesses > 127) {
ndbout_c("-proc flag requires a positive integer argument [1..127]");
return 1;
}
i += 2;
} else if (strcmp("-p", argv[i]) == 0){
if(i + 1 >= argc){
usage(argv[0]);
return 1;
}
if (sscanf(argv[i+1], "%d", &parallellism) == -1 ||
parallellism <= 0){
ndbout_c("-p flag requires a positive integer argument");
return 1;
}
i += 2;
}
else if (strcmp("-time",argv[i]) == 0) {
if (i + 1 >= argc) {
return 1;
}
if (sscanf(argv[i+1], "%d", &numSeconds) == -1 ||
numSeconds < 0) {
ndbout_c("-time flag requires a positive integer argument");
return 1;
}
i += 2;
}
else if (strcmp("-warm",argv[i]) == 0) {
if (i + 1 >= argc) {
return 1;
}
if (sscanf(argv[i+1], "%d", &numWarmSeconds) == -1 ||
numWarmSeconds < 0) {
ndbout_c("-warm flag requires a positive integer argument");
return 1;
}
i += 2;
}
else if (strcmp("-e",argv[i]) == 0) {
if (i + 1 >= argc) {
return 1;
}
if (sscanf(argv[i+1], "%d", &minEventSendPoll) == -1 ||
minEventSendPoll < 0) {
ndbout_c("-e flag requires a positive integer argument");
return 1;
}
i += 2;
}
else if (strcmp("-f",argv[i]) == 0) {
if (i + 1 >= argc) {
usage(argv[0]);
return 1;
}
if (sscanf(argv[i+1], "%d", &forceSendPoll) == -1 ||
forceSendPoll < 0) {
ndbout_c("-f flag requires a positive integer argument");
return 1;
}
i += 2;
}
else {
return 1;
}
}
if(minEventSendPoll > parallellism){
ndbout_c("minEventSendPoll(%d) > parallellism(%d)",
minEventSendPoll, parallellism);
ndbout_c("not very good...");
ndbout_c("very bad...");
ndbout_c("exiting...");
return 1;
}
return 0;
}
static
void
print_transaction(const char *header,
unsigned long totalCount,
TransactionDefinition *trans,
unsigned int printBranch,
unsigned int printRollback)
{
double f;
ndbout_c(" %s: %d (%.2f%%) "
"Latency(ms) avg: %d min: %d max: %d std: %d n: %d",
header,
trans->count,
(double)trans->count / (double)totalCount * 100.0,
(int)trans->latency.getMean(),
(int)trans->latency.getMin(),
(int)trans->latency.getMax(),
(int)trans->latency.getStddev(),
(int)trans->latency.getCount()
);
if( printBranch ){
if( trans->count == 0 )
f = 0.0;
else
f = (double)trans->branchExecuted / (double)trans->count * 100.0;
ndbout_c(" Branches Executed: %d (%.2f%%)", trans->branchExecuted, f);
}
if( printRollback ){
if( trans->count == 0 )
f = 0.0;
else
f = (double)trans->rollbackExecuted / (double)trans->count * 100.0;
ndbout_c(" Rollback Executed: %d (%.2f%%)",trans->rollbackExecuted,f);
}
}
void
print_stats(const char *title,
unsigned int length,
unsigned int transactionFlag,
GeneratorStatistics *gen,
int numProc, int parallellism)
{
int i;
char buf[10];
char name[MAXHOSTNAMELEN];
name[0] = 0;
NdbHost_GetHostName(name);
ndbout_c("\n------ %s ------",title);
ndbout_c("Length : %d %s",
length,
transactionFlag ? "Transactions" : "sec");
ndbout_c("Processor : %s", name);
ndbout_c("Number of Proc: %d",numProc);
ndbout_c("Parallellism : %d", parallellism);
ndbout_c("\n");
if( gen->totalTransactions == 0 ) {
ndbout_c(" No Transactions for this test");
}
else {
for(i = 0; i < 5; i++) {
sprintf(buf, "T%d",i+1);
print_transaction(buf,
gen->totalTransactions,
&gen->transactions[i],
i >= 2,
i >= 3 );
}
ndbout_c("\n");
ndbout_c(" Overall Statistics:");
ndbout_c(" Transactions: %d", gen->totalTransactions);
ndbout_c(" Outer : %.0f TPS",gen->outerTps);
ndbout_c("\n");
}
}
static
void *
threadRoutine(void *arg)
{
int i;
ThreadData *data = (ThreadData *)arg;
Ndb * pNDB;
pNDB = asyncDbConnect(parallellism);
/* NdbSleep_MilliSleep(rand() % 10); */
for(i = 0; i<parallellism; i++){
data[i].pNDB = pNDB;
}
millisSendPoll = 30000;
asyncGenerator(data, parallellism,
millisSendPoll, minEventSendPoll, forceSendPoll);
asyncDbDisconnect(pNDB);
return NULL;
}
NDB_COMMAND(DbAsyncGenerator, "DbAsyncGenerator",
"DbAsyncGenerator", "DbAsyncGenerator", 65535)
{
ndb_init();
int i;
int j;
int k;
struct NdbThread* pThread = NULL;
GeneratorStatistics stats;
GeneratorStatistics *p;
char threadName[32];
int rc = NDBT_OK;
void* tmp = NULL;
if(parse_args(argc,argv) != 0){
usage(argv[0]);
return NDBT_ProgramExit(NDBT_WRONGARGS);
}
ndbout_c("\nStarting Test with %d process(es) for %d %s parallellism %d",
numProcesses,
numSeconds,
"sec",
parallellism);
ndbout_c(" WarmUp/coolDown = %d sec", numWarmSeconds);
Ndb_cluster_connection con;
if(con.connect(12, 5, 1) != 0)
{
ndbout << "Unable to connect to management server." << endl;
return 0;
}
if (con.wait_until_ready(30,0) < 0)
{
ndbout << "Cluster nodes not ready in 30 seconds." << endl;
return 0;
}
g_cluster_connection= &con;
data = (ThreadData*)malloc((numProcesses*parallellism)*sizeof(ThreadData));
for(i = 0; i < numProcesses; i++) {
for(j = 0; j<parallellism; j++){
data[i*parallellism+j].warmUpSeconds = numWarmSeconds;
data[i*parallellism+j].testSeconds = numSeconds;
data[i*parallellism+j].coolDownSeconds = numWarmSeconds;
data[i*parallellism+j].randomSeed =
NdbTick_CurrentMillisecond()+i+j;
data[i*parallellism+j].changedTime = 0;
data[i*parallellism+j].runState = Runnable;
}
sprintf(threadName, "AsyncThread[%d]", i);
pThread = NdbThread_Create(threadRoutine,
(void**)&data[i*parallellism],
65535,
threadName,
NDB_THREAD_PRIO_LOW);
if(pThread != 0 && pThread != NULL){
(&data[i*parallellism])->pThread = pThread;
} else {
perror("Failed to create thread");
rc = NDBT_FAILED;
}
}
showTime();
/*--------------------------------*/
/* Wait for all processes to exit */
/*--------------------------------*/
for(i = 0; i < numProcesses; i++) {
NdbThread_WaitFor(data[i*parallellism].pThread, &tmp);
NdbThread_Destroy(&data[i*parallellism].pThread);
}
ndbout_c("All threads have finished");
/*-------------------------------------------*/
/* Clear all structures for total statistics */
/*-------------------------------------------*/
stats.totalTransactions = 0;
stats.outerTps = 0.0;
for(i = 0; i < NUM_TRANSACTION_TYPES; i++ ) {
stats.transactions[i].count = 0;
stats.transactions[i].branchExecuted = 0;
stats.transactions[i].rollbackExecuted = 0;
stats.transactions[i].latency.reset();
}
/*--------------------------------*/
/* Add the values for all Threads */
/*--------------------------------*/
for(i = 0; i < numProcesses; i++) {
for(k = 0; k<parallellism; k++){
p = &data[i*parallellism+k].generator;
stats.totalTransactions += p->totalTransactions;
stats.outerTps += p->outerTps;
for(j = 0; j < NUM_TRANSACTION_TYPES; j++ ) {
stats.transactions[j].count +=
p->transactions[j].count;
stats.transactions[j].branchExecuted +=
p->transactions[j].branchExecuted;
stats.transactions[j].rollbackExecuted +=
p->transactions[j].rollbackExecuted;
stats.transactions[j].latency +=
p->transactions[j].latency;
}
}
}
print_stats("Test Results",
numSeconds,
0,
&stats,
numProcesses,
parallellism);
free(data);
NDBT_ProgramExit(rc);
}
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <time.h>
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include "userInterface.h"
#include <NdbMutex.h>
#include <NdbThread.h>
#include <NdbTick.h>
#include <NdbApi.hpp>
#include <NdbOut.hpp>
/***************************************************************
* L O C A L C O N S T A N T S *
***************************************************************/
/***************************************************************
* L O C A L D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* L O C A L F U N C T I O N S *
***************************************************************/
#ifndef NDB_WIN32
#include <unistd.h>
#endif
Ndb*
asyncDbConnect(int parallellism){
Ndb * pNDB = new Ndb(g_cluster_connection, "TEST_DB");
pNDB->init(parallellism + 1);
while(pNDB->waitUntilReady() != 0){
}
return pNDB;
}
void
asyncDbDisconnect(Ndb* pNDB)
{
delete pNDB;
}
double
userGetTime(void)
{
static bool initialized = false;
static NDB_TICKS initSecs = 0;
static Uint32 initMicros = 0;
double timeValue = 0;
if ( !initialized ) {
initialized = true;
NdbTick_CurrentMicrosecond(&initSecs, &initMicros);
timeValue = 0.0;
} else {
NDB_TICKS secs = 0;
Uint32 micros = 0;
NdbTick_CurrentMicrosecond(&secs, &micros);
double s = (double)secs - (double)initSecs;
double us = (double)micros - (double)initMicros;
timeValue = s + (us / 1000000.0);
}
return timeValue;
}
void showTime()
{
char buf[128];
struct tm* tm_now;
time_t now;
now = ::time((time_t*)NULL);
tm_now = ::gmtime(&now);
::snprintf(buf, 128,
"%d-%.2d-%.2d %.2d:%.2d:%.2d",
tm_now->tm_year + 1900,
tm_now->tm_mon,
tm_now->tm_mday,
tm_now->tm_hour,
tm_now->tm_min,
tm_now->tm_sec);
ndbout_c("Time: %s", buf);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#include <ndb_global.h>
#include <ndb_opts.h>
#include "userInterface.h"
#include "dbPopulate.h"
#include <NdbMain.h>
#include <NdbOut.hpp>
#include <random.h>
#ifdef __cplusplus
extern "C" {
#endif
int useTableLogging;
int useIndexTables;
#ifdef __cplusplus
}
#endif
static void usage()
{
}
static
void usage(const char *prog)
{
ndbout_c(
"Usage: %s [-l]\n"
" -l Use logging and checkpointing on tables\n",
" -i Use index tables\n",
prog);
exit(1);
}
NDB_STD_OPTS_VARS;
NDB_COMMAND(DbCreate, "DbCreate", "DbCreate", "DbCreate", 16384)
{
int i;
UserHandle *uh;
useTableLogging = useIndexTables = 0;
NDB_INIT(argv[0]);
for(i = 1; i<argc; i++){
if(strcmp(argv[i], "-l") == 0){
useTableLogging = 1;
} else if(strcmp(argv[i], "-i") == 0){
useIndexTables = 1;
} else {
usage(argv[0]);
return 0;
}
}
ndbout_c("Using %s tables and %s key storage",
useTableLogging ? "logging" : "temporary",
useIndexTables ? "index" : "normal");
myRandom48Init(0x3e6f);
uh = userDbConnect(1, "TEST_DB");
dbPopulate(uh);
userDbDisconnect(uh);
return(0);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
#include "userInterface.h"
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <NdbApi.hpp>
inline
NdbConnection *
startTransaction(Ndb * pNDB,
ServerId inServerId,
const SubscriberNumber inNumber){
const int keyDataLenBytes = sizeof(ServerId)+SUBSCRIBER_NUMBER_LENGTH;
const int keyDataLen_64Words = keyDataLenBytes >> 3;
Uint64 keyDataBuf[keyDataLen_64Words+1]; // The "+1" is for rounding...
char * keyDataBuf_charP = (char *)&keyDataBuf[0];
Uint32 * keyDataBuf_wo32P = (Uint32 *)&keyDataBuf[0];
// Server Id comes first
keyDataBuf_wo32P[0] = inServerId;
// Then subscriber number
memcpy(&keyDataBuf_charP[sizeof(ServerId)], inNumber,
SUBSCRIBER_NUMBER_LENGTH);
return pNDB->startTransaction(0, keyDataBuf_charP, keyDataLenBytes);
}
void T1_Callback(int result, NdbConnection * pCon, void * threadData);
void T2_Callback(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_3(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_3(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_3(int result, NdbConnection * pCon, void * threadData);
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
void
start_T1(Ndb * pNDB, ThreadData * td){
DEBUG2("T1(%.*s): - Starting\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number);
int check;
NdbConnection * pCON = pNDB->startTransaction();
if (pCON != NULL) {
NdbOperation *MyOp = pCON->getNdbOperation(SUBSCRIBER_TABLE);
if (MyOp != NULL) {
MyOp->updateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->setValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->setValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
pCON->executeAsynchPrepare( Commit , T1_Callback, td);
} else {
CHECK_NULL(MyOp, "T1: getNdbOperation", pCON);
}//if
} else {
error_handler("T1-1: startTranscation",
pNDB->getNdbErrorString(),
pNDB->getNdbError());
}//if
}
void
T1_Callback(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG2("T1(%.*s): - Completing\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number);
CHECK_MINUS_ONE(result, "T1: Commit",
pCON);
td->pNDB->closeTransaction(pCON);
complete_T1(td);
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
void
start_T2(Ndb * pNDB, ThreadData * td){
DEBUG3("T2(%.*s, %p): - Starting\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.location);
int check;
NdbRecAttr * check2;
NdbConnection * pCON = pNDB->startTransaction();
if (pCON == NULL)
error_handler("T2-1: startTransaction",
pNDB->getNdbErrorString(),
pNDB->getNdbError());
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T2: getNdbOperation",
pCON);
MyOp->readTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_NAME,
td->transactionData.name);
pCON->executeAsynchPrepare( Commit, T2_Callback, td );
}
void
T2_Callback(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T2(%.*s, %p): - Completing\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.location);
CHECK_MINUS_ONE(result, "T2: Commit", pCON);
td->pNDB->closeTransaction(pCON);
complete_T2(td);
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
void
start_T3(Ndb * pNDB, ThreadData * td){
DEBUG3("T3(%.*s, %.2d): - Starting\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
int check;
NdbRecAttr * check2;
NdbConnection * pCON = startTransaction(pNDB,
td->transactionData.server_id,
td->transactionData.number);
if (pCON == NULL)
error_handler("T3-1: startTranscation",
pNDB->getNdbErrorString(),
pNDB->getNdbError());
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T3-1: getNdbOperation",
pCON);
MyOp->readTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
pCON->executeAsynchPrepare( NoCommit , T3_Callback_1, td);
}
void
T3_Callback_1(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T3(%.*s, %.2d): - Callback 1\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
CHECK_MINUS_ONE(result, "T3-1: NoCommit", pCON);
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T3-2: getNdbOperation",
pCON);
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_READ,
(char *)&td->transactionData.permission);
pCON->executeAsynchPrepare( NoCommit, T3_Callback_2, td );
}
void
T3_Callback_2(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
CHECK_MINUS_ONE(result, "T3-2: NoCommit", pCON);
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == server_bit)){
memcpy(td->transactionData.suffix,
&td->transactionData.number
[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T3(%.*s, %.2d): - Callback 2 - reading(%.*s)\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T3-3: getNdbOperation",
pCON);
MyOp->simpleRead();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
MyOp->getValue(IND_SESSION_DATA,
(char *)td->transactionData.session_details);
/* Operation 4 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T3-4: getNdbOperation",
pCON);
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_READS, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
DEBUG3("T3(%.*s, %.2d): - Callback 2 - no read\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->transactionData.branchExecuted = 0;
}
pCON->executeAsynchPrepare( Commit, T3_Callback_3, td );
}
void
T3_Callback_3(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T3(%.*s, %.2d): - Completing\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
CHECK_MINUS_ONE(result, "T3-3: Commit", pCON);
td->pNDB->closeTransaction(pCON);
complete_T3(td);
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
start_T4(Ndb * pNDB, ThreadData * td){
DEBUG3("T4(%.*s, %.2d): - Starting\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
int check;
NdbRecAttr * check2;
NdbConnection * pCON = startTransaction(pNDB,
td->transactionData.server_id,
td->transactionData.number);
if (pCON == NULL)
error_handler("T4-1: startTranscation",
pNDB->getNdbErrorString(),
pNDB->getNdbError());
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T4-1: getNdbOperation",
pCON);
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
MyOp->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)td->transactionData.server_bit);
pCON->executeAsynchPrepare( NoCommit , T4_Callback_1, td);
}
void
T4_Callback_1(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T4-1: NoCommit", pCON);
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T4(%.*s, %.2d): - Callback 1\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T4-2: getNdbOperation",
pCON);
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&td->transactionData.permission);
pCON->executeAsynchPrepare( NoCommit , T4_Callback_2, td);
}
void
T4_Callback_2(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T4-2: NoCommit", pCON);
ThreadData * td = (ThreadData *)threadData;
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == 0)){
memcpy(td->transactionData.suffix,
&td->transactionData.number
[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T4(%.*s, %.2d): - Callback 2 - inserting(%.*s)\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T4-3: getNdbOperation",
pCON);
MyOp->insertTuple();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
MyOp->setValue(SESSION_DATA,
(char *)td->transactionData.session_details);
/* Operation 4 */
/* Operation 5 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T4-5: getNdbOperation",
pCON);
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_INSERTS, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
td->transactionData.branchExecuted = 0;
DEBUG5("T4(%.*s, %.2d): - Callback 2 - %s %s\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
((permission & server_bit) ?
"permission - " : "no permission - "),
((sessions & server_bit) ?
"in session - " : "no in session - "));
}
if(!td->transactionData.do_rollback && td->transactionData.branchExecuted){
pCON->executeAsynchPrepare(Commit, T4_Callback_3, td);
} else {
pCON->executeAsynchPrepare(Rollback, T4_Callback_3, td);
}
}
void
T4_Callback_3(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T4-3: Commit", pCON);
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T4(%.*s, %.2d): - Completing\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->pNDB->closeTransaction(pCON);
complete_T4(td);
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
start_T5(Ndb * pNDB, ThreadData * td){
DEBUG3("T5(%.*s, %.2d): - Starting\n", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
int check;
NdbRecAttr * check2;
NdbConnection * pCON = pNDB->startTransaction();
if (pCON == NULL)
error_handler("T5-1: startTranscation",
pNDB->getNdbErrorString(),
pNDB->getNdbError());
NdbOperation * MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T5-1: getNdbOperation",
pCON);
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
MyOp->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)td->transactionData.server_bit);
pCON->executeAsynchPrepare( NoCommit, T5_Callback_1, td );
}
void
T5_Callback_1(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T5-1: NoCommit", pCON);
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T5(%.*s, %.2d): - Callback 1\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T5-2: getNdbOperation",
pCON);
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&td->transactionData.permission);
pCON->executeAsynchPrepare( NoCommit, T5_Callback_2, td );
}
void
T5_Callback_2(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T5-2: NoCommit", pCON);
ThreadData * td = (ThreadData *)threadData;
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == server_bit)){
memcpy(td->transactionData.suffix,
&td->transactionData.number
[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T5(%.*s, %.2d): - Callback 2 - deleting(%.*s)\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T5-3: getNdbOperation",
pCON);
MyOp->deleteTuple();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
/* Operation 4 */
/* Operation 5 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T5-5: getNdbOperation",
pCON);
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_DELETES, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
td->transactionData.branchExecuted = 0;
DEBUG5("T5(%.*s, %.2d): - Callback 2 - no delete - %s %s\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
((permission & server_bit) ?
"permission - " : "no permission - "),
((sessions & server_bit) ?
"in session - " : "no in session - "));
}
if(!td->transactionData.do_rollback && td->transactionData.branchExecuted){
pCON->executeAsynchPrepare(Commit, T5_Callback_3, td);
} else {
pCON->executeAsynchPrepare(Rollback, T5_Callback_3, td);
}
}
void
T5_Callback_3(int result, NdbConnection * pCON, void * threadData){
CHECK_MINUS_ONE(result, "T5-3: Commit", pCON);
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T5(%.*s, %.2d): - Completing\n",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->pNDB->closeTransaction(pCON);
complete_T5(td);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
#include <string.h>
#include "userInterface.h"
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <NdbSleep.h>
#include <NdbApi.hpp>
void T1_Callback(int result, NdbConnection * pCon, void * threadData);
void T2_Callback(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T3_Callback_3(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T4_Callback_3(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_1(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_2(int result, NdbConnection * pCon, void * threadData);
void T5_Callback_3(int result, NdbConnection * pCon, void * threadData);
static int stat_async = 0;
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
#define SFX_START (SUBSCRIBER_NUMBER_LENGTH - SUBSCRIBER_NUMBER_SUFFIX_LENGTH)
inline
NdbConnection *
startTransaction(Ndb * pNDB, ThreadData * td){
return pNDB->startTransaction();
#ifdef OLD_CODE
return pNDB->startTransactionDGroup (0,
&td->transactionData.number[SFX_START],
1);
#endif
}
void
start_T1(Ndb * pNDB, ThreadData * td, int async){
DEBUG2("T1(%.*s): - Starting", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number);
NdbConnection * pCON = 0;
while((pCON = startTransaction(pNDB, td)) == 0){
CHECK_ALLOWED_ERROR("T1: startTransaction", td, pNDB->getNdbError());
NdbSleep_MilliSleep(10);
}
NdbOperation *MyOp = pCON->getNdbOperation(SUBSCRIBER_TABLE);
if (MyOp != NULL) {
MyOp->updateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->setValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->setValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
if (async == 1) {
pCON->executeAsynchPrepare( Commit , T1_Callback, td);
} else {
int result = pCON->execute(Commit);
T1_Callback(result, pCON, (void*)td);
return;
}//if
} else {
CHECK_NULL(MyOp, "T1: getNdbOperation", td, pCON->getNdbError());
}//if
}
void
T1_Callback(int result, NdbConnection * pCON, void * threadData) {
ThreadData * td = (ThreadData *)threadData;
DEBUG2("T1(%.*s): - Completing", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number);
if (result == -1) {
CHECK_ALLOWED_ERROR("T1: Commit", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T1(td->pNDB, td, stat_async);
return;
}//if
td->pNDB->closeTransaction(pCON);
complete_T1(td);
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
void
start_T2(Ndb * pNDB, ThreadData * td, int async){
DEBUG3("T2(%.*s, %d): - Starting", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.location);
NdbConnection * pCON = 0;
while((pCON = startTransaction(pNDB, td)) == 0){
CHECK_ALLOWED_ERROR("T2-1: startTransaction", td, pNDB->getNdbError());
NdbSleep_MilliSleep(10);
}
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T2: getNdbOperation", td,
pCON->getNdbError());
MyOp->readTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_NAME,
td->transactionData.name);
if (async == 1) {
pCON->executeAsynchPrepare( Commit , T2_Callback, td);
} else {
int result = pCON->execute(Commit);
T2_Callback(result, pCON, (void*)td);
return;
}//if
}
void
T2_Callback(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T2(%.*s, %d): - Completing", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.location);
if (result == -1) {
CHECK_ALLOWED_ERROR("T2: Commit", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T2(td->pNDB, td, stat_async);
return;
}//if
td->pNDB->closeTransaction(pCON);
complete_T2(td);
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
void
start_T3(Ndb * pNDB, ThreadData * td, int async){
DEBUG3("T3(%.*s, %.2d): - Starting", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbConnection * pCON = 0;
while((pCON = startTransaction(pNDB, td)) == 0){
CHECK_ALLOWED_ERROR("T3-1: startTransaction", td, pNDB->getNdbError());
NdbSleep_MilliSleep(10);
}
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T3-1: getNdbOperation", td,
pCON->getNdbError());
MyOp->readTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
stat_async = async;
if (async == 1) {
pCON->executeAsynchPrepare( NoCommit , T3_Callback_1, td);
} else {
int result = pCON->execute( NoCommit );
T3_Callback_1(result, pCON, (void*)td);
return;
}//if
}
void
T3_Callback_1(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T3(%.*s, %.2d): - Callback 1", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
if (result == -1) {
CHECK_ALLOWED_ERROR("T3-1: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T3(td->pNDB, td, stat_async);
return;
}//if
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T3-2: getNdbOperation", td,
pCON->getNdbError());
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_READ,
(char *)&td->transactionData.permission);
if (stat_async == 1) {
pCON->executeAsynchPrepare( NoCommit , T3_Callback_2, td);
} else {
int result = pCON->execute( NoCommit );
T3_Callback_2(result, pCON, (void*)td);
return;
}//if
}
void
T3_Callback_2(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T3-2: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T3(td->pNDB, td, stat_async);
return;
}//if
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == server_bit)){
memcpy(td->transactionData.suffix,
&td->transactionData.number[SFX_START],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T3(%.*s, %.2d): - Callback 2 - reading(%.*s)",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T3-3: getNdbOperation", td,
pCON->getNdbError());
MyOp->simpleRead();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
MyOp->getValue(IND_SESSION_DATA,
(char *)td->transactionData.session_details);
/* Operation 4 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T3-4: getNdbOperation", td,
pCON->getNdbError());
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_READS, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
DEBUG3("T3(%.*s, %.2d): - Callback 2 - no read",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->transactionData.branchExecuted = 0;
}
if (stat_async == 1) {
pCON->executeAsynchPrepare( Commit , T3_Callback_3, td);
} else {
int result = pCON->execute( Commit );
T3_Callback_3(result, pCON, (void*)td);
return;
}//if
}
void
T3_Callback_3(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
DEBUG3("T3(%.*s, %.2d): - Completing", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
if (result == -1) {
CHECK_ALLOWED_ERROR("T3-3: Commit", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T3(td->pNDB, td, stat_async);
return;
}//if
td->pNDB->closeTransaction(pCON);
complete_T3(td);
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
start_T4(Ndb * pNDB, ThreadData * td, int async){
DEBUG3("T4(%.*s, %.2d): - Starting", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbConnection * pCON = 0;
while((pCON = startTransaction(pNDB, td)) == 0){
CHECK_ALLOWED_ERROR("T4-1: startTransaction", td, pNDB->getNdbError());
NdbSleep_MilliSleep(10);
}
NdbOperation *MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T4-1: getNdbOperation", td,
pCON->getNdbError());
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
MyOp->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)td->transactionData.server_bit);
stat_async = async;
if (async == 1) {
pCON->executeAsynchPrepare( NoCommit , T4_Callback_1, td);
} else {
int result = pCON->execute( NoCommit );
T4_Callback_1(result, pCON, (void*)td);
return;
}//if
}
void
T4_Callback_1(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T4-1: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T4(td->pNDB, td, stat_async);
return;
}//if
DEBUG3("T4(%.*s, %.2d): - Callback 1",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T4-2: getNdbOperation", td,
pCON->getNdbError());
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&td->transactionData.permission);
if (stat_async == 1) {
pCON->executeAsynchPrepare( NoCommit , T4_Callback_2, td);
} else {
int result = pCON->execute( NoCommit );
T4_Callback_2(result, pCON, (void*)td);
return;
}//if
}
void
T4_Callback_2(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T4-2: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T4(td->pNDB, td, stat_async);
return;
}//if
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == 0)){
memcpy(td->transactionData.suffix,
&td->transactionData.number[SFX_START],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T4(%.*s, %.2d): - Callback 2 - inserting(%.*s)",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T4-3: getNdbOperation", td,
pCON->getNdbError());
MyOp->insertTuple();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
MyOp->setValue(SESSION_DATA,
(char *)td->transactionData.session_details);
/* Operation 4 */
/* Operation 5 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T4-5: getNdbOperation", td,
pCON->getNdbError());
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_INSERTS, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
td->transactionData.branchExecuted = 0;
DEBUG5("T4(%.*s, %.2d): - Callback 2 - %s %s",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
((permission & server_bit) ?
"permission - " : "no permission - "),
((sessions & server_bit) ?
"in session - " : "no in session - "));
}
if(!td->transactionData.do_rollback && td->transactionData.branchExecuted){
if (stat_async == 1) {
pCON->executeAsynchPrepare( Commit , T4_Callback_3, td);
} else {
int result = pCON->execute( Commit );
T4_Callback_3(result, pCON, (void*)td);
return;
}//if
} else {
if (stat_async == 1) {
pCON->executeAsynchPrepare( Rollback , T4_Callback_3, td);
} else {
int result = pCON->execute( Rollback );
T4_Callback_3(result, pCON, (void*)td);
return;
}//if
}
}
void
T4_Callback_3(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T4-3: Commit", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T4(td->pNDB, td, stat_async);
return;
}//if
DEBUG3("T4(%.*s, %.2d): - Completing",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->pNDB->closeTransaction(pCON);
complete_T4(td);
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
start_T5(Ndb * pNDB, ThreadData * td, int async){
DEBUG3("T5(%.*s, %.2d): - Starting", SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbConnection * pCON = 0;
while((pCON = startTransaction(pNDB, td)) == 0){
CHECK_ALLOWED_ERROR("T5-1: startTransaction", td, pNDB->getNdbError());
NdbSleep_MilliSleep(10);
}
NdbOperation * MyOp= pCON->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOp, "T5-1: getNdbOperation", td,
pCON->getNdbError());
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SUBSCRIBER_NUMBER,
td->transactionData.number);
MyOp->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&td->transactionData.location);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_BY,
td->transactionData.changed_by);
MyOp->getValue(IND_SUBSCRIBER_CHANGED_TIME,
td->transactionData.changed_time);
MyOp->getValue(IND_SUBSCRIBER_GROUP,
(char *)&td->transactionData.group_id);
MyOp->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&td->transactionData.sessions);
MyOp->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)td->transactionData.server_bit);
stat_async = async;
if (async == 1) {
pCON->executeAsynchPrepare( NoCommit , T5_Callback_1, td);
} else {
int result = pCON->execute( NoCommit );
T5_Callback_1(result, pCON, (void*)td);
return;
}//if
}
void
T5_Callback_1(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T5-1: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T5(td->pNDB, td, stat_async);
return;
}//if
DEBUG3("T5(%.*s, %.2d): - Callback 1",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
NdbOperation * MyOp = pCON->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOp, "T5-2: getNdbOperation", td,
pCON->getNdbError());
MyOp->readTuple();
MyOp->equal(IND_GROUP_ID,
(char*)&td->transactionData.group_id);
MyOp->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&td->transactionData.permission);
if (stat_async == 1) {
pCON->executeAsynchPrepare( NoCommit , T5_Callback_2, td);
} else {
int result = pCON->execute( NoCommit );
T5_Callback_2(result, pCON, (void*)td);
return;
}//if
}
void
T5_Callback_2(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T5-2: execute", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T5(td->pNDB, td, stat_async);
return;
}//if
Uint32 permission = td->transactionData.permission;
Uint32 sessions = td->transactionData.sessions;
Uint32 server_bit = td->transactionData.server_bit;
if(((permission & server_bit) == server_bit) &&
((sessions & server_bit) == server_bit)){
memcpy(td->transactionData.suffix,
&td->transactionData.number[SFX_START],
SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG5("T5(%.*s, %.2d): - Callback 2 - deleting(%.*s)",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
td->transactionData.suffix);
/* Operation 3 */
NdbOperation * MyOp = pCON->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOp, "T5-3: getNdbOperation", td,
pCON->getNdbError());
MyOp->deleteTuple();
MyOp->equal(IND_SESSION_SUBSCRIBER,
(char*)td->transactionData.number);
MyOp->equal(IND_SESSION_SERVER,
(char*)&td->transactionData.server_id);
/* Operation 4 */
/* Operation 5 */
MyOp = pCON->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOp, "T5-5: getNdbOperation", td,
pCON->getNdbError());
MyOp->interpretedUpdateTuple();
MyOp->equal(IND_SERVER_ID,
(char*)&td->transactionData.server_id);
MyOp->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)td->transactionData.suffix);
MyOp->incValue(IND_SERVER_DELETES, (uint32)1);
td->transactionData.branchExecuted = 1;
} else {
td->transactionData.branchExecuted = 0;
DEBUG5("T5(%.*s, %.2d): - Callback 2 - no delete - %s %s",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id,
((permission & server_bit) ?
"permission - " : "no permission - "),
((sessions & server_bit) ?
"in session - " : "no in session - "));
}
if(!td->transactionData.do_rollback && td->transactionData.branchExecuted){
if (stat_async == 1) {
pCON->executeAsynchPrepare( Commit , T5_Callback_3, td);
} else {
int result = pCON->execute( Commit );
T5_Callback_3(result, pCON, (void*)td);
return;
}//if
} else {
if (stat_async == 1) {
pCON->executeAsynchPrepare( Rollback , T5_Callback_3, td);
} else {
int result = pCON->execute( Rollback );
T5_Callback_3(result, pCON, (void*)td);
return;
}//if
}
}
void
T5_Callback_3(int result, NdbConnection * pCON, void * threadData){
ThreadData * td = (ThreadData *)threadData;
if (result == -1) {
CHECK_ALLOWED_ERROR("T5-3: Commit", td, pCON->getNdbError());
td->pNDB->closeTransaction(pCON);
start_T5(td->pNDB, td, stat_async);
return;
}//if
DEBUG3("T5(%.*s, %.2d): - Completing",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number,
td->transactionData.server_id);
td->pNDB->closeTransaction(pCON);
complete_T5(td);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef NDB_ERROR_H
#define NDB_ERROR_H
#include <ndb_global.h>
#include <NdbOut.hpp>
#include "userInterface.h"
#include <NdbError.hpp>
#include <NdbApi.hpp>
#define error_handler(x,y, z) { \
ndbout << x << " " << y << endl; \
exit(-1); }
#define CHECK_MINUS_ONE(x, y, z) if(x == -1) \
error_handler(y,(z->getNdbError()), 0)
inline
void
CHECK_ALLOWED_ERROR(const char * str,
const ThreadData * td,
const struct NdbError & error){
char buf[100];
snprintf(buf, sizeof(buf), "subscriber = %.*s ",
SUBSCRIBER_NUMBER_LENGTH,
td->transactionData.number);
ndbout << str << " " << error << endl
<< buf;
showTime();
switch(error.classification) {
case NdbError::TimeoutExpired:
case NdbError::OverloadError:
case NdbError::TemporaryResourceError:
case NdbError::NodeRecoveryError:
break;
default:
if(error.status != NdbError::TemporaryError)
exit(-1);
}
}
inline
void
CHECK_NULL(void * null,
const char * str,
const ThreadData * td,
const struct NdbError & err){
if(null == 0){
CHECK_ALLOWED_ERROR(str, td, err);
exit(-1);
}
}
inline
void
CHECK_NULL(void * null, const char* msg, NdbConnection* obj)
{
if(null == 0)
{
error_handler(msg, obj->getNdbError(), 0);
}
}
#endif
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef NDB_SCHEMA_H
#define NDB_SCHEMA_H
#include "testDefinitions.h"
#define SUBSCRIBER_TABLE "SUBSCRIBER"
#define SUBSCRIBER_NUMBER "NUMBER"
#define SUBSCRIBER_LOCATION "LOCATION"
#define SUBSCRIBER_NAME "NAME"
#define SUBSCRIBER_GROUP "GROUP_ID"
#define SUBSCRIBER_SESSIONS "SESSIONS"
#define SUBSCRIBER_CHANGED_BY "CHANGED_BY"
#define SUBSCRIBER_CHANGED_TIME "CHANGED_TIME"
#define SERVER_TABLE "SERVER"
#define SERVER_ID "SERVER_ID"
#define SERVER_SUBSCRIBER_SUFFIX "SUFFIX"
#define SERVER_NAME "NAME"
#define SERVER_READS "NO_OF_READ"
#define SERVER_INSERTS "NO_OF_INSERT"
#define SERVER_DELETES "NO_OF_DELETE"
#define GROUP_TABLE "GROUP"
#define GROUP_ID "GROUP_ID"
#define GROUP_NAME "GROUP_NAME"
#define GROUP_ALLOW_READ "ALLOW_READ"
#define GROUP_ALLOW_INSERT "ALLOW_INSERT"
#define GROUP_ALLOW_DELETE "ALLOW_DELETE"
#define SESSION_TABLE "SESSION"
#define SESSION_SERVER "SERVER_ID"
#define SESSION_SUBSCRIBER "NUMBER"
#define SESSION_DATA "DATA"
/** Numbers */
#define IND_SUBSCRIBER_NUMBER (unsigned)0
#define IND_SUBSCRIBER_NAME (unsigned)1
#define IND_SUBSCRIBER_GROUP (unsigned)2
#define IND_SUBSCRIBER_LOCATION (unsigned)3
#define IND_SUBSCRIBER_SESSIONS (unsigned)4
#define IND_SUBSCRIBER_CHANGED_BY (unsigned)5
#define IND_SUBSCRIBER_CHANGED_TIME (unsigned)6
#define IND_SERVER_SUBSCRIBER_SUFFIX (unsigned)0
#define IND_SERVER_ID (unsigned)1
#define IND_SERVER_NAME (unsigned)2
#define IND_SERVER_READS (unsigned)3
#define IND_SERVER_INSERTS (unsigned)4
#define IND_SERVER_DELETES (unsigned)5
#define IND_GROUP_ID (unsigned)0
#define IND_GROUP_NAME (unsigned)1
#define IND_GROUP_ALLOW_READ (unsigned)2
#define IND_GROUP_ALLOW_INSERT (unsigned)3
#define IND_GROUP_ALLOW_DELETE (unsigned)4
#define IND_SESSION_SUBSCRIBER (unsigned)0
#define IND_SESSION_SERVER (unsigned)1
#define IND_SESSION_DATA (unsigned)2
#endif
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
extern "C" {
#include "user_transaction.h"
};
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <time.h>
#include <NdbApi.hpp>
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
int
T1(void * obj,
const SubscriberNumber number,
const Location new_location,
const ChangedBy changed_by,
const ChangedTime changed_time,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
check = MyOperation->updateTuple();
CHECK_MINUS_ONE(check, "T1: updateTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T1: equal subscriber",
MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_LOCATION,
(char *)&new_location);
CHECK_MINUS_ONE(check, "T1: setValue location",
MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_MINUS_ONE(check, "T1: setValue changed_by",
MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_MINUS_ONE(check, "T1: setValue changed_time",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
int
T2(void * obj,
const SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T2: readTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T2: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_LOCATION,
(char *)readLocation);
CHECK_NULL(check2, "T2: getValue location",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_NULL(check2, "T2: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_NULL(check2, "T2: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_NAME,
subscriberName);
CHECK_NULL(check2, "T2: getValue name",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
int
T3(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
SessionDetails outSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-1: readTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T3-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T3-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T3-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T3-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T3-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T3-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-2: readTuple",
MyTransaction);
check = MyOperation->equal(GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T3-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(GROUP_ALLOW_READ,
(char *)&permission);
CHECK_NULL(check2, "T3-2: getValue allow_read",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("reading - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-3: readTuple",
MyTransaction);
check = MyOperation->equal(SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T3-3: equal number",
MyTransaction);
check = MyOperation->equal(SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-3: equal server id",
MyTransaction);
check2 = MyOperation->getValue(SESSION_DATA,
(char *)outSessionDetails);
CHECK_NULL(check2, "T3-3: getValue session details",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T3-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-4: equal serverId",
MyTransaction);
check = MyOperation->equal(SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T3-4: equal suffix",
MyTransaction);
check = MyOperation->incValue(SERVER_READS, (uint32)1);
CHECK_MINUS_ONE(check, "T3-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-4: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T4(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
const SessionDetails inSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), 0);
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
NdbOperation * MyOperation = 0;
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T4-1: readTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T4-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T4-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T4-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T4-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T4-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T4-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T4-2: readTuple",
MyTransaction);
check = MyOperation->equal(GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T4-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(GROUP_ALLOW_INSERT,
(char *)&permission);
CHECK_NULL(check2, "T4-2: getValue allow_insert",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
DEBUG("inserting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "T4-3: insertTuple",
MyTransaction);
check = MyOperation->equal(SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-3: equal number",
MyTransaction);
check = MyOperation->equal(SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-3: equal server id",
MyTransaction);
check = MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
CHECK_MINUS_ONE(check, "T4-3: setValue session details",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-4: equal number",
MyTransaction);
check = MyOperation->incValue(SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T4-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-4: NoCommit",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-5: equal serverId",
MyTransaction);
check = MyOperation->equal(SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T4-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(SERVER_INSERTS, (uint32)1);
CHECK_MINUS_ONE(check, "T4-5: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-5: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T5(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), 0);
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T5-1: readTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T5-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T5-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T5-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T5-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T5-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T5-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T5-2: readTuple",
MyTransaction);
check = MyOperation->equal(GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T5-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(GROUP_ALLOW_DELETE,
(char *)&permission);
CHECK_NULL(check2, "T5-2: getValue allow_delete",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("deleting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
check = MyOperation->deleteTuple();
CHECK_MINUS_ONE(check, "T5-3: deleteTuple",
MyTransaction);
check = MyOperation->equal(SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-3: equal number",
MyTransaction);
check = MyOperation->equal(SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-3: equal server id",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-4: equal number",
MyTransaction);
check = MyOperation->subValue(SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T5-4: dec value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-4: NoCommit",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-5: equal serverId",
MyTransaction);
check = MyOperation->equal(SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T5-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(SERVER_DELETES, (uint32)1);
CHECK_MINUS_ONE(check, "T5-5: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-5: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
extern "C" {
#include "user_transaction.h"
};
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <time.h>
#include <NdbApi.hpp>
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
int
T1(void * obj,
const SubscriberNumber number,
const Location new_location,
const ChangedBy changed_by,
const ChangedTime changed_time,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
check = MyOperation->updateTuple();
CHECK_MINUS_ONE(check, "T1: updateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T1: equal subscriber",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&new_location);
CHECK_MINUS_ONE(check, "T1: setValue location",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_MINUS_ONE(check, "T1: setValue changed_by",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_MINUS_ONE(check, "T1: setValue changed_time",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
int
T2(void * obj,
const SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T2: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)readLocation);
CHECK_NULL(check2, "T2: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_NULL(check2, "T2: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_NULL(check2, "T2: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_NAME,
subscriberName);
CHECK_NULL(check2, "T2: getValue name",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
int
T3(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
SessionDetails outSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T3-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T3-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T3-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T3-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T3-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T3-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T3-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_READ,
(char *)&permission);
CHECK_NULL(check2, "T3-2: getValue allow_read",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("reading - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-3: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T3-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-3: equal server id",
MyTransaction);
check2 = MyOperation->getValue(IND_SESSION_DATA,
(char *)outSessionDetails);
CHECK_NULL(check2, "T3-3: getValue session details",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T3-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-4: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T3-4: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_READS, (uint32)1);
CHECK_MINUS_ONE(check, "T3-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-4: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T4(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
const SessionDetails inSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), 0);
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
NdbOperation * MyOperation = 0;
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T4-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T4-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T4-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T4-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T4-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T4-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T4-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T4-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T4-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&permission);
CHECK_NULL(check2, "T4-2: getValue allow_insert",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
DEBUG("inserting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "T4-3: insertTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-3: equal server id",
MyTransaction);
check = MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
CHECK_MINUS_ONE(check, "T4-3: setValue session details",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-4: equal number",
MyTransaction);
check = MyOperation->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T4-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-4: NoCommit",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T4-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_INSERTS, (uint32)1);
CHECK_MINUS_ONE(check, "T4-5: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-5: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T5(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), 0);
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T5-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T5-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T5-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T5-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T5-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T5-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T5-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T5-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T5-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&permission);
CHECK_NULL(check2, "T5-2: getValue allow_delete",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("deleting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
check = MyOperation->deleteTuple();
CHECK_MINUS_ONE(check, "T5-3: deleteTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-3: equal server id",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-3: NoCommit",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-4: equal number",
MyTransaction);
check = MyOperation->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T5-4: dec value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-4: NoCommit",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T5-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_DELETES, (uint32)1);
CHECK_MINUS_ONE(check, "T5-5: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-5: NoCommit",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
extern "C" {
#include "user_transaction.h"
};
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <time.h>
#include <NdbApi.hpp>
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
int
T1(void * obj,
const SubscriberNumber number,
const Location new_location,
const ChangedBy changed_by,
const ChangedTime changed_time,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
check = MyOperation->updateTuple();
CHECK_MINUS_ONE(check, "T1: updateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T1: equal subscriber",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&new_location);
CHECK_MINUS_ONE(check, "T1: setValue location",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_MINUS_ONE(check, "T1: setValue changed_by",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_MINUS_ONE(check, "T1: setValue changed_time",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
int
T2(void * obj,
const SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T2: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)readLocation);
CHECK_NULL(check2, "T2: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_NULL(check2, "T2: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_NULL(check2, "T2: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_NAME,
subscriberName);
CHECK_NULL(check2, "T2: getValue name",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
int
T3(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
SessionDetails outSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T3-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T3-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T3-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T3-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T3-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T3-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T3-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_READ,
(char *)&permission);
CHECK_NULL(check2, "T3-2: getValue allow_read",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("reading - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-3: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T3-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-3: equal server id",
MyTransaction);
check2 = MyOperation->getValue(IND_SESSION_DATA,
(char *)outSessionDetails);
CHECK_NULL(check2, "T3-3: getValue session details",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T3-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-4: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T3-4: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_READS, (uint32)1);
CHECK_MINUS_ONE(check, "T3-4: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T4(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
const SessionDetails inSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), 0);
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
NdbOperation * MyOperation = 0;
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T4-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T4-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T4-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T4-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T4-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T4-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T4-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T4-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T4-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&permission);
CHECK_NULL(check2, "T4-2: getValue allow_insert",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
DEBUG("inserting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "T4-3: insertTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-3: equal server id",
MyTransaction);
check = MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
CHECK_MINUS_ONE(check, "T4-3: setValue session details",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-4: equal number",
MyTransaction);
check = MyOperation->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T4-4: inc value",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T4-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_INSERTS, (uint32)1);
CHECK_MINUS_ONE(check, "T4-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T5(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), 0);
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTupleExclusive();
CHECK_MINUS_ONE(check, "T5-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T5-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T5-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T5-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T5-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T5-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T5-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T5-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T5-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&permission);
CHECK_NULL(check2, "T5-2: getValue allow_delete",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("deleting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
check = MyOperation->deleteTuple();
CHECK_MINUS_ONE(check, "T5-3: deleteTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-3: equal server id",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-4: equal number",
MyTransaction);
check = MyOperation->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T5-4: dec value",
MyTransaction);
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T5-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_DELETES, (uint32)1);
CHECK_MINUS_ONE(check, "T5-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
extern "C" {
#include "user_transaction.h"
};
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <time.h>
#include <NdbApi.hpp>
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
int
T1(void * obj,
const SubscriberNumber number,
const Location new_location,
const ChangedBy changed_by,
const ChangedTime changed_time,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
DEBUG2("T1(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T1-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
check = MyOperation->updateTuple();
CHECK_MINUS_ONE(check, "T1: updateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T1: equal subscriber",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&new_location);
CHECK_MINUS_ONE(check, "T1: setValue location",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_MINUS_ONE(check, "T1: setValue changed_by",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_MINUS_ONE(check, "T1: setValue changed_time",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
int
T2(void * obj,
const SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
DEBUG2("T2(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T2: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)readLocation);
CHECK_NULL(check2, "T2: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_NULL(check2, "T2: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_NULL(check2, "T2: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_NAME,
subscriberName);
CHECK_NULL(check2, "T2: getValue name",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
int
T3(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
SessionDetails outSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T3-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T3-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T3-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T3-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T3-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T3-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T3-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_READ,
(char *)&permission);
CHECK_NULL(check2, "T3-2: getValue allow_read",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("reading - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-3: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T3-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-3: equal server id",
MyTransaction);
check2 = MyOperation->getValue(IND_SESSION_DATA,
(char *)outSessionDetails);
CHECK_NULL(check2, "T3-3: getValue session details",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T3-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-4: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T3-4: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_READS, (uint32)1);
CHECK_MINUS_ONE(check, "T3-4: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit...");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
DEBUG("done\n");
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T4(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
const SessionDetails inSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T4-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T4-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T4-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T4-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T4-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T4-1: getValue sessions",
MyTransaction);
check = MyOperation->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T4-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T4-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T4-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&permission);
CHECK_NULL(check2, "T4-2: getValue allow_insert",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
DEBUG("inserting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "T4-3: insertTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-3: equal server id",
MyTransaction);
check = MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
CHECK_MINUS_ONE(check, "T4-3: setValue session details",
MyTransaction);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T4-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_INSERTS, (uint32)1);
CHECK_MINUS_ONE(check, "T4-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T5(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
Ndb * pNDB = (Ndb *) obj;
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), 0);
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T5-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T5-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T5-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T5-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T5-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T5-1: getValue sessions",
MyTransaction);
check = MyOperation->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T5-4: dec value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T5-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T5-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&permission);
CHECK_NULL(check2, "T5-2: getValue allow_delete",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("deleting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
check = MyOperation->deleteTuple();
CHECK_MINUS_ONE(check, "T5-3: deleteTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-3: equal server id",
MyTransaction);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T5-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_DELETES, (uint32)1);
CHECK_MINUS_ONE(check, "T5-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
extern "C" {
#include "user_transaction.h"
};
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <time.h>
#include <NdbApi.hpp>
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
int
T1(void * obj,
const SubscriberNumber number,
const Location new_location,
const ChangedBy changed_by,
const ChangedTime changed_time,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
DEBUG2("T1(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T1-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
check = MyOperation->updateTuple();
CHECK_MINUS_ONE(check, "T1: updateTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T1: equal subscriber",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&new_location);
CHECK_MINUS_ONE(check, "T1: setValue location",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_MINUS_ONE(check, "T1: setValue changed_by",
MyTransaction);
check = MyOperation->setValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_MINUS_ONE(check, "T1: setValue changed_time",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
int
T2(void * obj,
const SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName,
BenchmarkTime * transaction_time){
Ndb * pNDB = (Ndb *) obj;
DEBUG2("T2(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
CHECK_MINUS_ONE(check, "T2: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)readLocation);
CHECK_NULL(check2, "T2: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
CHECK_NULL(check2, "T2: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
CHECK_NULL(check2, "T2: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_NAME,
subscriberName);
CHECK_NULL(check2, "T2: getValue name",
MyTransaction);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
get_time(transaction_time);
time_diff(transaction_time, &start);
return 0;
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
int
T3(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
SessionDetails outSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T3-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T3-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T3-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T3-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T3-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T3-1: getValue sessions",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T3-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T3-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_READ,
(char *)&permission);
CHECK_NULL(check2, "T3-2: getValue allow_read",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("reading - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
check = MyOperation->simpleRead();
CHECK_MINUS_ONE(check, "T3-3: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T3-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-3: equal server id",
MyTransaction);
check2 = MyOperation->getValue(IND_SESSION_DATA,
(char *)outSessionDetails);
CHECK_NULL(check2, "T3-3: getValue session details",
MyTransaction);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T3-4: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T3-4: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T3-4: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_READS, (uint32)1);
CHECK_MINUS_ONE(check, "T3-4: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit...");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
DEBUG("done\n");
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T4(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
const SessionDetails inSessionDetails,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), 0);
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T4-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T4-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T4-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T4-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T4-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T4-1: getValue sessions",
MyTransaction);
check = MyOperation->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T4-4: inc value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T4-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T4-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&permission);
CHECK_NULL(check2, "T4-2: getValue allow_insert",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
DEBUG("inserting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "T4-3: insertTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T4-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-3: equal server id",
MyTransaction);
check = MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
CHECK_MINUS_ONE(check, "T4-3: setValue session details",
MyTransaction);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T4-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T4-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T4-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_INSERTS, (uint32)1);
CHECK_MINUS_ONE(check, "T4-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
int
T5(void * obj,
const SubscriberNumber inNumber,
const SubscriberSuffix inSuffix,
const ServerId inServerId,
const ServerBit inServerBit,
ChangedBy outChangedBy,
ChangedTime outChangedTime,
Location * outLocation,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted,
BenchmarkTime * outTransactionTime){
Ndb * pNDB = (Ndb *) obj;
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
BenchmarkTime start;
get_time(&start);
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), 0);
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-1: readTuple",
MyTransaction);
check = MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
CHECK_MINUS_ONE(check, "T5-1: equal subscriber",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)outLocation);
CHECK_NULL(check2, "T5-1: getValue location",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
CHECK_NULL(check2, "T5-1: getValue changed_by",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
CHECK_NULL(check2, "T5-1: getValue changed_time",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
CHECK_NULL(check2, "T5-1: getValue group",
MyTransaction);
check2 = MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
CHECK_NULL(check2, "T5-1: getValue sessions",
MyTransaction);
check = MyOperation->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
CHECK_MINUS_ONE(check, "T5-4: dec value",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
check = MyOperation->readTuple();
CHECK_MINUS_ONE(check, "T5-2: readTuple",
MyTransaction);
check = MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
CHECK_MINUS_ONE(check, "T5-2: equal group",
MyTransaction);
check2 = MyOperation->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&permission);
CHECK_NULL(check2, "T5-2: getValue allow_delete",
MyTransaction);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
DEBUG("deleting - ");
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
check = MyOperation->deleteTuple();
CHECK_MINUS_ONE(check, "T5-3: deleteTuple",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
CHECK_MINUS_ONE(check, "T5-3: equal number",
MyTransaction);
check = MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-3: equal server id",
MyTransaction);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
check = MyOperation->interpretedUpdateTuple();
CHECK_MINUS_ONE(check, "T5-5: interpretedUpdateTuple",
MyTransaction);
check = MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
CHECK_MINUS_ONE(check, "T5-5: equal serverId",
MyTransaction);
check = MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
CHECK_MINUS_ONE(check, "T5-5: equal suffix",
MyTransaction);
check = MyOperation->incValue(IND_SERVER_DELETES, (uint32)1);
CHECK_MINUS_ONE(check, "T5-5: inc value",
MyTransaction);
(* outBranchExecuted) = 1;
} else {
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
(* outBranchExecuted) = 0;
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
get_time(outTransactionTime);
time_diff(outTransactionTime, &start);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
//#define DEBUG_ON
#include <string.h>
#include "userHandle.h"
#include "userInterface.h"
#include "macros.h"
#include "ndb_schema.hpp"
#include "ndb_error.hpp"
#include <NdbApi.hpp>
void
userCheckpoint(UserHandle *uh){
}
inline
NdbConnection *
startTransaction(Ndb * pNDB, ServerId inServerId, const SubscriberNumber inNumber){
const int keyDataLenBytes = sizeof(ServerId)+SUBSCRIBER_NUMBER_LENGTH;
const int keyDataLen_64Words = keyDataLenBytes >> 3;
Uint64 keyDataBuf[keyDataLen_64Words+1]; // The "+1" is for rounding...
char * keyDataBuf_charP = (char *)&keyDataBuf[0];
Uint32 * keyDataBuf_wo32P = (Uint32 *)&keyDataBuf[0];
// Server Id comes first
keyDataBuf_wo32P[0] = inServerId;
// Then subscriber number
memcpy(&keyDataBuf_charP[sizeof(ServerId)], inNumber, SUBSCRIBER_NUMBER_LENGTH);
return pNDB->startTransaction(0, keyDataBuf_charP, keyDataLenBytes);
}
/**
* Transaction 1 - T1
*
* Update location and changed by/time on a subscriber
*
* Input:
* SubscriberNumber,
* Location,
* ChangedBy,
* ChangedTime
*
* Output:
*/
void
userTransaction_T1(UserHandle * uh,
SubscriberNumber number,
Location new_location,
ChangedBy changed_by,
ChangedTime changed_time){
Ndb * pNDB = uh->pNDB;
DEBUG2("T1(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction != NULL) {
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
if (MyOperation != NULL) {
MyOperation->updateTuple();
MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
MyOperation->setValue(IND_SUBSCRIBER_LOCATION,
(char *)&new_location);
MyOperation->setValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
MyOperation->setValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
check = MyTransaction->execute( Commit );
if (check != -1) {
pNDB->closeTransaction(MyTransaction);
return;
} else {
CHECK_MINUS_ONE(check, "T1: Commit",
MyTransaction);
}//if
} else {
CHECK_NULL(MyOperation, "T1: getNdbOperation", MyTransaction);
}//if
} else {
error_handler("T1-1: startTranscation", pNDB->getNdbErrorString(), pNDB->getNdbError());
}//if
}
/**
* Transaction 2 - T2
*
* Read from Subscriber:
*
* Input:
* SubscriberNumber
*
* Output:
* Location
* Changed by
* Changed Timestamp
* Name
*/
void
userTransaction_T2(UserHandle * uh,
SubscriberNumber number,
Location * readLocation,
ChangedBy changed_by,
ChangedTime changed_time,
SubscriberName subscriberName){
Ndb * pNDB = uh->pNDB;
DEBUG2("T2(%.*s):\n", SUBSCRIBER_NUMBER_LENGTH, number);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T2-1: startTransaction", pNDB->getNdbErrorString(), pNDB->getNdbError());
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T2: getNdbOperation",
MyTransaction);
MyOperation->readTuple();
MyOperation->equal(IND_SUBSCRIBER_NUMBER,
number);
MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)readLocation);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
changed_by);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
changed_time);
MyOperation->getValue(IND_SUBSCRIBER_NAME,
subscriberName);
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T2: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
}
/**
* Transaction 3 - T3
*
* Read session details
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
*
* Output:
* BranchExecuted
* SessionDetails
* ChangedBy
* ChangedTime
* Location
*/
void
userTransaction_T3(UserHandle * uh,
SubscriberNumber inNumber,
ServerId inServerId,
ServerBit inServerBit,
SessionDetails outSessionDetails,
BranchExecuted * outBranchExecuted){
Ndb * pNDB = uh->pNDB;
char outChangedBy [sizeof(ChangedBy) +(4-(sizeof(ChangedBy) & 3))];
char outChangedTime [sizeof(ChangedTime)+(4-(sizeof(ChangedTime) & 3))];
Location outLocation;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
SubscriberSuffix inSuffix;
DEBUG3("T3(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = startTransaction(pNDB, inServerId, inNumber);
if (MyTransaction == NULL)
error_handler("T3-1: startTranscation", pNDB->getNdbErrorString(), pNDB->getNdbError());
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T3-1: getNdbOperation",
MyTransaction);
MyOperation->readTuple();
MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&outLocation);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-1: NoCommit",
MyTransaction);
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T3-2: getNdbOperation",
MyTransaction);
MyOperation->readTuple();
MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
MyOperation->getValue(IND_GROUP_ALLOW_READ,
(char *)&permission);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T3-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
memcpy(inSuffix,
&inNumber[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH], SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG2("reading(%.*s) - ", SUBSCRIBER_NUMBER_SUFFIX_LENGTH, inSuffix);
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T3-3: getNdbOperation",
MyTransaction);
MyOperation->simpleRead();
MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
MyOperation->getValue(IND_SESSION_DATA,
(char *)outSessionDetails);
/* Operation 4 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T3-4: getNdbOperation",
MyTransaction);
MyOperation->interpretedUpdateTuple();
MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
MyOperation->incValue(IND_SERVER_READS, (uint32)1);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
}
DEBUG("commit...");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T3: Commit",
MyTransaction);
pNDB->closeTransaction(MyTransaction);
DEBUG("done\n");
}
/**
* Transaction 4 - T4
*
* Create session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* SessionDetails,
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
userTransaction_T4(UserHandle * uh,
SubscriberNumber inNumber,
ServerId inServerId,
ServerBit inServerBit,
SessionDetails inSessionDetails,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted){
Ndb * pNDB = uh->pNDB;
char outChangedBy [sizeof(ChangedBy) +(4-(sizeof(ChangedBy) & 3))];
char outChangedTime [sizeof(ChangedTime)+(4-(sizeof(ChangedTime) & 3))];
Location outLocation;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
SubscriberSuffix inSuffix;
DEBUG3("T4(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
int check;
NdbRecAttr * check2;
NdbConnection * MyTransaction = startTransaction(pNDB, inServerId, inNumber);
if (MyTransaction == NULL)
error_handler("T4-1: startTranscation", pNDB->getNdbErrorString(), pNDB->getNdbError());
NdbOperation *MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T4-1: getNdbOperation",
MyTransaction);
MyOperation->interpretedUpdateTuple();
MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&outLocation);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
outChangedBy);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
outChangedTime);
MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
MyOperation->incValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
check = MyTransaction->execute( NoCommit );
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T4-2: getNdbOperation",
MyTransaction);
MyOperation->readTuple();
MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
MyOperation->getValue(IND_GROUP_ALLOW_INSERT,
(char *)&permission);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T4-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == 0)){
memcpy(inSuffix,
&inNumber[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH], SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG2("inserting(%.*s) - ", SUBSCRIBER_NUMBER_SUFFIX_LENGTH, inSuffix);
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T4-3: getNdbOperation",
MyTransaction);
MyOperation->insertTuple();
MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
MyOperation->setValue(SESSION_DATA,
(char *)inSessionDetails);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T4-5: getNdbOperation",
MyTransaction);
MyOperation->interpretedUpdateTuple();
MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
MyOperation->incValue(IND_SERVER_INSERTS, (uint32)1);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T4: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T4:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
}
/**
* Transaction 5 - T5
*
* Delete session
*
* Input:
* SubscriberNumber
* ServerId
* ServerBit
* DoRollback
* Output:
* ChangedBy
* ChangedTime
* Location
* BranchExecuted
*/
void
userTransaction_T5(UserHandle * uh,
SubscriberNumber inNumber,
ServerId inServerId,
ServerBit inServerBit,
DoRollback inDoRollback,
BranchExecuted * outBranchExecuted){
Ndb * pNDB = uh->pNDB;
DEBUG3("T5(%.*s, %.2d): ", SUBSCRIBER_NUMBER_LENGTH, inNumber, inServerId);
NdbConnection * MyTransaction = 0;
NdbOperation * MyOperation = 0;
char outChangedBy [sizeof(ChangedBy) +(4-(sizeof(ChangedBy) & 3))];
char outChangedTime [sizeof(ChangedTime)+(4-(sizeof(ChangedTime) & 3))];
Location outLocation;
GroupId groupId;
ActiveSessions sessions;
Permission permission;
SubscriberSuffix inSuffix;
int check;
NdbRecAttr * check2;
MyTransaction = pNDB->startTransaction();
if (MyTransaction == NULL)
error_handler("T5-1: startTranscation", pNDB->getNdbErrorString(), pNDB->getNdbError());
MyOperation= MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "T5-1: getNdbOperation",
MyTransaction);
MyOperation->interpretedUpdateTuple();
MyOperation->equal(IND_SUBSCRIBER_NUMBER,
inNumber);
MyOperation->getValue(IND_SUBSCRIBER_LOCATION,
(char *)&outLocation);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_BY,
&outChangedBy[0]);
MyOperation->getValue(IND_SUBSCRIBER_CHANGED_TIME,
&outChangedTime[0]);
MyOperation->getValue(IND_SUBSCRIBER_GROUP,
(char *)&groupId);
MyOperation->getValue(IND_SUBSCRIBER_SESSIONS,
(char *)&sessions);
MyOperation->subValue(IND_SUBSCRIBER_SESSIONS,
(uint32)inServerBit);
MyTransaction->execute( NoCommit );
/* Operation 2 */
MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "T5-2: getNdbOperation",
MyTransaction);
MyOperation->readTuple();
MyOperation->equal(IND_GROUP_ID,
(char*)&groupId);
MyOperation->getValue(IND_GROUP_ALLOW_DELETE,
(char *)&permission);
check = MyTransaction->execute( NoCommit );
CHECK_MINUS_ONE(check, "T5-2: NoCommit",
MyTransaction);
if(((permission & inServerBit) == inServerBit) &&
((sessions & inServerBit) == inServerBit)){
memcpy(inSuffix,
&inNumber[SUBSCRIBER_NUMBER_LENGTH-SUBSCRIBER_NUMBER_SUFFIX_LENGTH], SUBSCRIBER_NUMBER_SUFFIX_LENGTH);
DEBUG2("deleting(%.*s) - ", SUBSCRIBER_NUMBER_SUFFIX_LENGTH, inSuffix);
/* Operation 3 */
MyOperation = MyTransaction->getNdbOperation(SESSION_TABLE);
CHECK_NULL(MyOperation, "T5-3: getNdbOperation",
MyTransaction);
MyOperation->deleteTuple();
MyOperation->equal(IND_SESSION_SUBSCRIBER,
(char*)inNumber);
MyOperation->equal(IND_SESSION_SERVER,
(char*)&inServerId);
/* Operation 4 */
/* Operation 5 */
MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "T5-5: getNdbOperation",
MyTransaction);
MyOperation->interpretedUpdateTuple();
MyOperation->equal(IND_SERVER_ID,
(char*)&inServerId);
MyOperation->equal(IND_SERVER_SUBSCRIBER_SUFFIX,
(char*)inSuffix);
MyOperation->incValue(IND_SERVER_DELETES, (uint32)1);
(* outBranchExecuted) = 1;
} else {
(* outBranchExecuted) = 0;
DEBUG1("%s", ((permission & inServerBit) ? "permission - " : "no permission - "));
DEBUG1("%s", ((sessions & inServerBit) ? "in session - " : "no in session - "));
}
if(!inDoRollback && (* outBranchExecuted)){
DEBUG("commit\n");
check = MyTransaction->execute( Commit );
CHECK_MINUS_ONE(check, "T5: Commit",
MyTransaction);
} else {
DEBUG("rollback\n");
check = MyTransaction->execute(Rollback);
CHECK_MINUS_ONE(check, "T5:Rollback",
MyTransaction);
}
pNDB->closeTransaction(MyTransaction);
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef TESTDATA_H
#define TESTDATA_H
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include <NdbTick.h>
#include <NdbThread.h>
#include <NDBT_Stats.hpp>
#include <random.h>
#include "testDefinitions.h"
/***************************************************************
* M A C R O S *
***************************************************************/
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
#define NUM_TRANSACTION_TYPES 5
#define SESSION_LIST_LENGTH 1000
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
typedef struct {
SubscriberNumber subscriberNumber;
ServerId serverId;
} SessionElement;
typedef struct {
SessionElement list[SESSION_LIST_LENGTH];
unsigned int readIndex;
unsigned int writeIndex;
unsigned int numberInList;
} SessionList;
typedef struct {
unsigned int count;
unsigned int branchExecuted;
unsigned int rollbackExecuted;
/**
* Latency measures
*/
NDB_TICKS startTime;
NDBT_Stats latency;
unsigned int latencyCounter;
inline void startLatency(){
if((latencyCounter & 127) == 127)
startTime = NdbTick_CurrentMillisecond();
}
inline void stopLatency(){
if((latencyCounter & 127) == 127){
const NDB_TICKS tmp = NdbTick_CurrentMillisecond() - startTime;
latency.addObservation(tmp);
}
latencyCounter++;
}
} TransactionDefinition;
typedef struct {
RandomSequence transactionSequence;
RandomSequence rollbackSequenceT4;
RandomSequence rollbackSequenceT5;
TransactionDefinition transactions[NUM_TRANSACTION_TYPES];
unsigned int totalTransactions;
double outerLoopTime;
double outerTps;
SessionList activeSessions;
} GeneratorStatistics;
typedef enum{
Runnable,
Running
} RunState ;
typedef struct {
SubscriberNumber number;
SubscriberSuffix suffix;
SubscriberName name;
Location location;
ChangedBy changed_by;
ChangedTime changed_time;
ServerId server_id;
ServerBit server_bit;
SessionDetails session_details;
GroupId group_id;
ActiveSessions sessions;
Permission permission;
unsigned int do_rollback;
unsigned int branchExecuted;
unsigned int sessionElement;
} TransactionData ;
typedef struct {
struct NdbThread* pThread;
unsigned long randomSeed;
unsigned long changedTime;
unsigned int warmUpSeconds;
unsigned int testSeconds;
unsigned int coolDownSeconds;
GeneratorStatistics generator;
/**
* For async execution
*/
RunState runState;
double startTime;
TransactionData transactionData;
struct Ndb * pNDB;
} ThreadData;
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
/***************************************************************
* E X T E R N A L D A T A *
***************************************************************/
#endif /* TESTDATA_H */
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef TESTDEFINITIONS_H
#define TESTDEFINITIONS_H
/***************************************************************/
/* I N C L U D E D F I L E S */
/***************************************************************/
#include <ndb_types.h>
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
#define OP_PER_TRANS 200
#define NO_OF_SUBSCRIBERS 500000
#define NO_OF_GROUPS 100
#define NO_OF_SERVERS 20
#define SUBSCRIBER_NUMBER_LENGTH 12
#define SUBSCRIBER_NUMBER_SUFFIX_LENGTH 2
#define SUBSCRIBER_NAME_LENGTH 32
#define CHANGED_BY_LENGTH 32
#define CHANGED_TIME_LENGTH 32
#define SESSION_DETAILS_LENGTH 2000
#define SERVER_NAME_LENGTH 32
#define GROUP_NAME_LENGTH 32
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
#define PADDING 4
typedef char SubscriberNumber[SUBSCRIBER_NUMBER_LENGTH];
typedef char SubscriberSuffix[SUBSCRIBER_NUMBER_SUFFIX_LENGTH + 2];
typedef char SubscriberName[SUBSCRIBER_NAME_LENGTH];
typedef char ServerName[SERVER_NAME_LENGTH];
typedef char GroupName[GROUP_NAME_LENGTH];
typedef char ChangedBy[CHANGED_BY_LENGTH];
typedef char ChangedTime[CHANGED_TIME_LENGTH];
typedef char SessionDetails[SESSION_DETAILS_LENGTH];
typedef Uint32 ServerId;
typedef Uint32 ServerBit;
typedef Uint32 GroupId;
typedef Uint32 Location;
typedef Uint32 Permission;
typedef Uint32 Counter;
typedef Uint32 ActiveSessions;
typedef unsigned int BranchExecuted;
typedef unsigned int DoRollback;
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
#ifdef __cplusplus
extern "C" {
#endif
#ifdef __cplusplus
}
#endif
/***************************************************************
* E X T E R N A L D A T A *
***************************************************************/
#endif /* TESTDEFINITIONS_H */
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/***************************************************************
* I N C L U D E D F I L E S *
***************************************************************/
#include <ndb_global.h>
#ifndef NDB_WIN32
#include <sys/time.h>
#endif
#include "ndb_error.hpp"
#include "userInterface.h"
#include <NdbThread.h>
#include <NdbTick.h>
#include <NdbMutex.h>
#include <NdbSleep.h>
#include "ndb_schema.hpp"
#include <NDBT.hpp>
#include <NdbSchemaCon.hpp>
/***************************************************************
* L O C A L C O N S T A N T S *
***************************************************************/
/***************************************************************
* L O C A L D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* L O C A L F U N C T I O N S *
***************************************************************/
extern int localDbPrepare(UserHandle *uh);
static int dbCreate(UserHandle *uh);
/***************************************************************
* L O C A L D A T A *
***************************************************************/
/***************************************************************
* P U B L I C D A T A *
***************************************************************/
/***************************************************************
****************************************************************
* L O C A L F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
/***************************************************************
****************************************************************
* P U B L I C F U N C T I O N S C O D E S E C T I O N *
****************************************************************
***************************************************************/
/*-----------------------------------*/
/* Time related Functions */
/* */
/* Returns a double value in seconds */
/*-----------------------------------*/
double userGetTimeSync(void)
{
static int initialized = 0;
static NDB_TICKS initSecs = 0;
static Uint32 initMicros = 0;
double timeValue = 0;
if ( !initialized ) {
initialized = 1;
NdbTick_CurrentMicrosecond(&initSecs, &initMicros);
timeValue = 0.0;
} else {
NDB_TICKS secs = 0;
Uint32 micros = 0;
NdbTick_CurrentMicrosecond(&secs, &micros);
double s = (double)secs - (double)initSecs;
double us = (double)secs - (double)initMicros;
timeValue = s + (us / 1000000.0);
}
return timeValue;
}
// 0 - OK
// 1 - Retry transaction
// 2 - Permanent
int
userDbCommit(UserHandle *uh){
if(uh->pCurrTrans != 0){
int check = uh->pCurrTrans->execute( Commit );
NdbError err = uh->pCurrTrans->getNdbError();
uh->pNDB->closeTransaction(uh->pCurrTrans);
uh->pCurrTrans = 0;
if(err.status != NdbError::Success)
ndbout << err << endl;
if(err.status == NdbError::TemporaryError &&
err.classification == NdbError::OverloadError){
NdbSleep_SecSleep(3);
}
return err.status;
}
return 2;
}
/**
* TRUE - Normal table
* FALSE - Table w.o. checkpoing and logging
*/
#ifdef __cplusplus
extern "C" {
#endif
extern int useTableLogging;
extern int useIndexTables;
#ifdef __cplusplus
}
#endif
int
create_table_server(Ndb * pNdb){
int check;
NdbSchemaCon * MySchemaTransaction = NdbSchemaCon::startSchemaTrans(pNdb);
if( MySchemaTransaction == NULL )
error_handler("startSchemaTransaction", pNdb->getNdbError(), 0);
NdbSchemaOp * MySchemaOp = MySchemaTransaction->getNdbSchemaOp();
if( MySchemaOp == NULL )
error_handler("getNdbSchemaOp", MySchemaTransaction->getNdbError(), 0);
// Create table
check = MySchemaOp->createTable( SERVER_TABLE,
8, // Table size
TupleKey, // Key Type
1 // Nr of Pages
,DistributionGroup,
6,
78,
80,
1,
useTableLogging
);
if( check == -1 )
error_handler("createTable", MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute
( SERVER_SUBSCRIBER_SUFFIX,
TupleKey,
sizeof(char) << 3,
SUBSCRIBER_NUMBER_SUFFIX_LENGTH,
String,
MMBased,
NotNullAttribute,
NormalStorageAttribute,
0,
1,
16);
if( check == -1 )
error_handler("createAttribute (subscriber suffix)",
MySchemaTransaction->getNdbError(), 0);
// Create first column, primary key
check = MySchemaOp->createAttribute( SERVER_ID,
TupleKey,
sizeof(ServerId) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (serverid)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SERVER_NAME,
NoKey,
sizeof(char) << 3,
SERVER_NAME_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (server name)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SERVER_READS,
NoKey,
sizeof(Counter) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (server reads)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SERVER_INSERTS,
NoKey,
sizeof(Counter) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (server inserts)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SERVER_DELETES,
NoKey,
sizeof(Counter) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (server deletes)",
MySchemaTransaction->getNdbError(), 0);
if( MySchemaTransaction->execute() == -1 ) {
error_handler("schemaTransaction->execute()",
MySchemaTransaction->getNdbError(), 0);
}
NdbSchemaCon::closeSchemaTrans(MySchemaTransaction);
return 0;
}
int
create_table_group(Ndb * pNdb){
int check;
NdbSchemaCon * MySchemaTransaction = NdbSchemaCon::startSchemaTrans(pNdb);
if( MySchemaTransaction == NULL )
error_handler("startSchemaTransaction", pNdb->getNdbError(), 0);
NdbSchemaOp * MySchemaOp = MySchemaTransaction->getNdbSchemaOp();
if( MySchemaOp == NULL )
error_handler("getNdbSchemaOp", MySchemaTransaction->getNdbError(), 0);
// Create table
check = MySchemaOp->createTable( GROUP_TABLE,
8, // Table size
TupleKey, // Key Type
1 // Nr of Pages
,All,
6,
78,
80,
1,
useTableLogging
);
if( check == -1 )
error_handler("createTable", MySchemaTransaction->getNdbError(), 0);
// Create first column, primary key
check = MySchemaOp->createAttribute( GROUP_ID,
TupleKey,
sizeof(GroupId) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (group id)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( GROUP_NAME,
NoKey,
sizeof(char) << 3,
GROUP_NAME_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (group name)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( GROUP_ALLOW_READ,
NoKey,
sizeof(Permission) << 3,
1,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (group read)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( GROUP_ALLOW_INSERT,
NoKey,
sizeof(Permission) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (group insert)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( GROUP_ALLOW_DELETE,
NoKey,
sizeof(Permission) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (group delete)",
MySchemaTransaction->getNdbError(), 0);
if( MySchemaTransaction->execute() == -1 ) {
error_handler("schemaTransaction->execute()",
MySchemaTransaction->getNdbError(), 0);
}
NdbSchemaCon::closeSchemaTrans(MySchemaTransaction);
return 0;
}
int
create_table_subscriber(Ndb * pNdb){
int check;
NdbSchemaCon * MySchemaTransaction = NdbSchemaCon::startSchemaTrans(pNdb);
if( MySchemaTransaction == NULL )
error_handler("startSchemaTransaction", pNdb->getNdbError(), 0);
NdbSchemaOp * MySchemaOp = MySchemaTransaction->getNdbSchemaOp();
if( MySchemaOp == NULL )
error_handler("getNdbSchemaOp", MySchemaTransaction->getNdbError(), 0);
// Create table
check = MySchemaOp->createTable( SUBSCRIBER_TABLE,
8, // Table size
TupleKey, // Key Type
1 // Nr of Pages
,DistributionGroup,
6,
78,
80,
1,
useTableLogging
);
if( check == -1 )
error_handler("createTable", MySchemaTransaction->getNdbError(), 0);
// Create first column, primary key
check = MySchemaOp->createAttribute
( SUBSCRIBER_NUMBER,
TupleKey,
sizeof(char) << 3,
SUBSCRIBER_NUMBER_LENGTH,
String,
MMBased,
NotNullAttribute,
(useIndexTables ? IndexStorageAttribute : NormalStorageAttribute),
0,
1,
16);
if( check == -1 )
error_handler("createAttribute (subscriber number)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_NAME,
NoKey,
sizeof(char) << 3,
SUBSCRIBER_NAME_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (subscriber name)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_GROUP,
NoKey,
sizeof(GroupId) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (subscriber_group)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_LOCATION,
NoKey,
sizeof(Location) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (server reads)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_SESSIONS,
NoKey,
sizeof(ActiveSessions) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (subscriber_sessions)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_CHANGED_BY,
NoKey,
sizeof(char) << 3,
CHANGED_BY_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (subscriber_changed_by)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SUBSCRIBER_CHANGED_TIME,
NoKey,
sizeof(char) << 3,
CHANGED_TIME_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (subscriber_changed_time)",
MySchemaTransaction->getNdbError(), 0);
if( MySchemaTransaction->execute() == -1 ) {
error_handler("schemaTransaction->execute()",
MySchemaTransaction->getNdbError(), 0);
}
NdbSchemaCon::closeSchemaTrans(MySchemaTransaction);
return 0;
}
int
create_table_session(Ndb * pNdb){
int check;
NdbSchemaCon * MySchemaTransaction = NdbSchemaCon::startSchemaTrans(pNdb);
if( MySchemaTransaction == NULL )
error_handler("startSchemaTransaction", pNdb->getNdbError(), 0);
NdbSchemaOp * MySchemaOp = MySchemaTransaction->getNdbSchemaOp();
if( MySchemaOp == NULL )
error_handler("getNdbSchemaOp",
MySchemaTransaction->getNdbError(), 0);
// Create table
check = MySchemaOp->createTable( SESSION_TABLE,
8, // Table size
TupleKey, // Key Type
1 // Nr of Pages
,DistributionGroup,
6,
78,
80,
1,
useTableLogging
);
if( check == -1 )
error_handler("createTable", MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SESSION_SUBSCRIBER,
TupleKey,
sizeof(char) << 3,
SUBSCRIBER_NUMBER_LENGTH,
String,
MMBased,
NotNullAttribute,
NormalStorageAttribute,
0,
1,
16);
if( check == -1 )
error_handler("createAttribute (session_subscriber)",
MySchemaTransaction->getNdbError(), 0);
// Create first column, primary key
check = MySchemaOp->createAttribute( SESSION_SERVER,
TupleKey,
sizeof(ServerId) << 3,
1,
UnSigned,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (session_server)",
MySchemaTransaction->getNdbError(), 0);
check = MySchemaOp->createAttribute( SESSION_DATA,
NoKey,
sizeof(char) << 3,
SESSION_DETAILS_LENGTH,
String,
MMBased,
NotNullAttribute );
if( check == -1 )
error_handler("createAttribute (session_data)",
MySchemaTransaction->getNdbError(), 0);
if( MySchemaTransaction->execute() == -1 ) {
error_handler("schemaTransaction->execute()",
MySchemaTransaction->getNdbError(), 0);
}
NdbSchemaCon::closeSchemaTrans(MySchemaTransaction);
return 0;
}
void
create_table(const char * name, int (* function)(Ndb * pNdb), Ndb* pNdb){
printf("creating table %s...", name);
if(pNdb->getDictionary()->getTable(name) != 0){
printf(" it already exists\n");
return;
} else {
printf("\n");
}
function(pNdb);
printf("creating table %s... done\n", name);
}
static int dbCreate(Ndb * pNdb)
{
create_table(SUBSCRIBER_TABLE, create_table_subscriber, pNdb);
create_table(GROUP_TABLE , create_table_group, pNdb);
create_table(SESSION_TABLE , create_table_session, pNdb);
create_table(SERVER_TABLE , create_table_server, pNdb);
return 0;
}
#ifndef NDB_WIN32
#include <unistd.h>
#endif
UserHandle*
userDbConnect(uint32 createDb, char *dbName)
{
Ndb_cluster_connection *con= new Ndb_cluster_connection();
if(con->connect(12, 5, 1) != 0)
{
ndbout << "Unable to connect to management server." << endl;
return 0;
}
if (con->wait_until_ready(30,0) < 0)
{
ndbout << "Cluster nodes not ready in 30 seconds." << endl;
return 0;
}
Ndb * pNdb = new Ndb(con, dbName);
//printf("Initializing...\n");
pNdb->init();
//printf("Waiting...");
while(pNdb->waitUntilReady() != 0){
//printf("...");
}
// printf("done\n");
if( createDb )
dbCreate(pNdb);
UserHandle * uh = new UserHandle;
uh->pNCC = con;
uh->pNDB = pNdb;
uh->pCurrTrans = 0;
return uh;
}
void userDbDisconnect(UserHandle *uh)
{
delete uh;
}
int userDbInsertServer(UserHandle *uh,
ServerId serverId,
SubscriberSuffix suffix,
ServerName name)
{
int check;
uint32 noOfRead = 0;
uint32 noOfInsert = 0;
uint32 noOfDelete = 0;
NdbConnection * MyTransaction = 0;
if(uh->pCurrTrans != 0){
MyTransaction = uh->pCurrTrans;
} else {
uh->pCurrTrans = MyTransaction = uh->pNDB->startTransaction();
}
if (MyTransaction == NULL)
error_handler("startTranscation", uh->pNDB->getNdbError(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SERVER_TABLE);
CHECK_NULL(MyOperation, "getNdbOperation", MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "insert tuple", MyTransaction);
check = MyOperation->equal(SERVER_ID, (char*)&serverId);
CHECK_MINUS_ONE(check, "setValue id", MyTransaction);
check = MyOperation->setValue(SERVER_SUBSCRIBER_SUFFIX, suffix);
CHECK_MINUS_ONE(check, "setValue suffix", MyTransaction);
check = MyOperation->setValue(SERVER_NAME, name);
CHECK_MINUS_ONE(check, "setValue name", MyTransaction);
check = MyOperation->setValue(SERVER_READS, (char*)&noOfRead);
CHECK_MINUS_ONE(check, "setValue reads", MyTransaction);
check = MyOperation->setValue(SERVER_INSERTS, (char*)&noOfInsert);
CHECK_MINUS_ONE(check, "setValue inserts", MyTransaction);
check = MyOperation->setValue(SERVER_DELETES, (char*)&noOfDelete);
CHECK_MINUS_ONE(check, "setValue deletes", MyTransaction);
return 0;
}
int userDbInsertSubscriber(UserHandle *uh,
SubscriberNumber number,
uint32 groupId,
SubscriberName name)
{
int check;
uint32 activeSessions = 0;
Location l = 0;
ChangedBy changedBy; snprintf(changedBy, sizeof(changedBy), "ChangedBy");
ChangedTime changedTime; snprintf(changedTime, sizeof(changedTime), "ChangedTime");
NdbConnection * MyTransaction = 0;
if(uh->pCurrTrans != 0){
MyTransaction = uh->pCurrTrans;
} else {
uh->pCurrTrans = MyTransaction = uh->pNDB->startTransaction();
}
if (MyTransaction == NULL)
error_handler("startTranscation", uh->pNDB->getNdbError(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(SUBSCRIBER_TABLE);
CHECK_NULL(MyOperation, "getNdbOperation", MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "insertTuple", MyTransaction);
check = MyOperation->equal(SUBSCRIBER_NUMBER, number);
CHECK_MINUS_ONE(check, "equal", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_NAME, name);
CHECK_MINUS_ONE(check, "setValue name", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_GROUP, (char*)&groupId);
CHECK_MINUS_ONE(check, "setValue group", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_LOCATION, (char*)&l);
CHECK_MINUS_ONE(check, "setValue location", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_SESSIONS, (char*)&activeSessions);
CHECK_MINUS_ONE(check, "setValue sessions", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_CHANGED_BY, changedBy);
CHECK_MINUS_ONE(check, "setValue changedBy", MyTransaction);
check = MyOperation->setValue(SUBSCRIBER_CHANGED_TIME, changedTime);
CHECK_MINUS_ONE(check, "setValue changedTime", MyTransaction);
return 0;
}
int userDbInsertGroup(UserHandle *uh,
GroupId groupId,
GroupName name,
Permission allowRead,
Permission allowInsert,
Permission allowDelete)
{
int check;
NdbConnection * MyTransaction = 0;
if(uh->pCurrTrans != 0){
MyTransaction = uh->pCurrTrans;
} else {
uh->pCurrTrans = MyTransaction = uh->pNDB->startTransaction();
}
if (MyTransaction == NULL)
error_handler("startTranscation", uh->pNDB->getNdbError(), 0);
NdbOperation *MyOperation = MyTransaction->getNdbOperation(GROUP_TABLE);
CHECK_NULL(MyOperation, "getNdbOperation", MyTransaction);
check = MyOperation->insertTuple();
CHECK_MINUS_ONE(check, "insertTuple", MyTransaction);
check = MyOperation->equal(GROUP_ID, (char*)&groupId);
CHECK_MINUS_ONE(check, "equal", MyTransaction);
check = MyOperation->setValue(GROUP_NAME, name);
CHECK_MINUS_ONE(check, "setValue name", MyTransaction);
check = MyOperation->setValue(GROUP_ALLOW_READ, (char*)&allowRead);
CHECK_MINUS_ONE(check, "setValue allowRead", MyTransaction);
check = MyOperation->setValue(GROUP_ALLOW_INSERT, (char*)&allowInsert);
CHECK_MINUS_ONE(check, "setValue allowInsert", MyTransaction);
check = MyOperation->setValue(GROUP_ALLOW_DELETE, (char*)&allowDelete);
CHECK_MINUS_ONE(check, "setValue allowDelete", MyTransaction);
return 0;
}
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef DBINTERFACE_H
#define DBINTERFACE_H
/***************************************************************/
/* I N C L U D E D F I L E S */
/***************************************************************/
#include "testDefinitions.h"
#include "testData.h"
/***************************************************************
* M A C R O S *
***************************************************************/
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
/*-----------------------*/
/* Default Database Name */
/*-----------------------*/
#define DEFAULTDB "TestDbClient"
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
typedef struct Ndb Ndb;
#ifdef __cplusplus
extern "C" {
#endif
extern void showTime();
extern double userGetTime(void);
extern Ndb *asyncDbConnect(int parallellism);
extern void asyncDbDisconnect(Ndb* pNDB);
extern void start_T1(Ndb * uh, ThreadData * data, int async);
extern void start_T2(Ndb * uh, ThreadData * data, int async);
extern void start_T3(Ndb * uh, ThreadData * data, int async);
extern void start_T4(Ndb * uh, ThreadData * data, int async);
extern void start_T5(Ndb * uh, ThreadData * data, int async);
extern void complete_T1(ThreadData * data);
extern void complete_T2(ThreadData * data);
extern void complete_T3(ThreadData * data);
extern void complete_T4(ThreadData * data);
extern void complete_T5(ThreadData * data);
#ifdef __cplusplus
}
#endif
/***************************************************************/
/* I N C L U D E D F I L E S */
/***************************************************************/
#include "testDefinitions.h"
/***************************************************************
* M A C R O S *
***************************************************************/
/***************************************************************/
/* C O N S T A N T S */
/***************************************************************/
/*-----------------------*/
/* Default Database Name */
/*-----------------------*/
#define DEFAULTDB "TestDbClient"
/***************************************************************
* D A T A S T R U C T U R E S *
***************************************************************/
typedef struct {
struct Ndb_cluster_connection* pNCC;
struct Ndb * pNDB;
struct NdbTransaction * pCurrTrans;
} UserHandle;
/***************************************************************
* P U B L I C F U N C T I O N S *
***************************************************************/
#ifdef __cplusplus
extern "C" {
#endif
extern double userGetTimeSync(void);
extern void userCheckpoint(UserHandle *uh);
extern UserHandle *userDbConnect(uint32 createDb, char *dbName);
extern void userDbDisconnect(UserHandle *uh);
extern int userDbInsertServer(UserHandle *uh,
ServerId serverId,
SubscriberSuffix suffix,
ServerName name);
extern int userDbInsertSubscriber(UserHandle *uh,
SubscriberNumber number,
uint32 groupId,
SubscriberName name);
extern int userDbInsertGroup(UserHandle *uh,
GroupId groupId,
GroupName name,
Permission allowRead,
Permission allowInsert,
Permission allowDelete);
extern int userDbCommit(UserHandle *uh);
extern int userDbRollback(UserHandle *uh);
#ifdef __cplusplus
}
#endif
/***************************************************************
* E X T E R N A L D A T A *
***************************************************************/
#endif /* DBINTERFACE_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment