mirror of
https://github.com/MariaDB/server.git
synced 2025-07-29 05:21:33 +03:00
testIndex -n NFNR1
Bugs in scan(tc) nf-handling(api) exec-handling(tc) ndb/include/ndbapi/NdbConnection.hpp: Allow dropped signal during NF handling ndb/include/ndbapi/NdbOperation.hpp: Add option to allow dropped signals ndb/src/kernel/blocks/dbtc/DbtcMain.cpp: 1) Printer for state 2) New option to sendtckeyconf (index) - clear exec flag 3) Moved init of *global* apiConnectptr to prevent errornous scan_tabconf ARGH!!! ndb/src/ndbapi/NdbConnection.cpp: Move abort from checkState_trans since it can be ok with "illegal" signals during NF handling ndb/src/ndbapi/NdbConnectionScan.cpp: Move abort from checkState_trans since it can be ok with "illegal" signals during NF handling ndb/src/ndbapi/Ndbif.cpp: 1) Indentation 2) Better handling of TCKEY_FAILCONF - always ack commit ack marker even if transaction has already been removed 3) abort on 4012 (VM_TRACE) ndb/src/ndbapi/TransporterFacade.cpp: Don't trace APIREG_REQ/CONF by default ndb/test/include/NDBT_Test.hpp: Atomic decProperty (used for semaphore impl.) ndb/test/ndbapi/testIndex.cpp: Impl. option to sync restarts ndb/test/src/NDBT_Test.cpp: Atomic decProperty
This commit is contained in:
@ -693,9 +693,6 @@ NdbConnection::checkState_TransId(const Uint32 * transId) const {
|
||||
const Uint32 tTmp2 = transId[1];
|
||||
Uint64 tRecTransId = (Uint64)tTmp1 + ((Uint64)tTmp2 << 32);
|
||||
bool b = theStatus == Connected && theTransactionId == tRecTransId;
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
if(!b) abort();
|
||||
#endif
|
||||
return b;
|
||||
}
|
||||
|
||||
|
@ -755,7 +755,7 @@ protected:
|
||||
int receiveREAD_CONF(const Uint32* aDataPtr, Uint32 aDataLength);
|
||||
|
||||
|
||||
int checkMagicNumber(); // Verify correct object
|
||||
int checkMagicNumber(bool b = true); // Verify correct object
|
||||
|
||||
int checkState_TransId(NdbApiSignal* aSignal);
|
||||
|
||||
@ -900,11 +900,11 @@ protected:
|
||||
|
||||
inline
|
||||
int
|
||||
NdbOperation::checkMagicNumber()
|
||||
NdbOperation::checkMagicNumber(bool b)
|
||||
{
|
||||
if (theMagicNumber != 0xABCDEF01){
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
if(b) abort();
|
||||
#endif
|
||||
return -1;
|
||||
}
|
||||
|
@ -79,7 +79,36 @@
|
||||
#ifdef VM_TRACE
|
||||
NdbOut &
|
||||
operator<<(NdbOut& out, Dbtc::ConnectionState state){
|
||||
out << (int)state;
|
||||
switch(state){
|
||||
case Dbtc::CS_CONNECTED: out << "CS_CONNECTED"; break;
|
||||
case Dbtc::CS_DISCONNECTED: out << "CS_DISCONNECTED"; break;
|
||||
case Dbtc::CS_STARTED: out << "CS_STARTED"; break;
|
||||
case Dbtc::CS_RECEIVING: out << "CS_RECEIVING"; break;
|
||||
case Dbtc::CS_PREPARED: out << "CS_PREPARED"; break;
|
||||
case Dbtc::CS_START_PREPARING: out << "CS_START_PREPARING"; break;
|
||||
case Dbtc::CS_REC_PREPARING: out << "CS_REC_PREPARING"; break;
|
||||
case Dbtc::CS_RESTART: out << "CS_RESTART"; break;
|
||||
case Dbtc::CS_ABORTING: out << "CS_ABORTING"; break;
|
||||
case Dbtc::CS_COMPLETING: out << "CS_COMPLETING"; break;
|
||||
case Dbtc::CS_COMPLETE_SENT: out << "CS_COMPLETE_SENT"; break;
|
||||
case Dbtc::CS_PREPARE_TO_COMMIT: out << "CS_PREPARE_TO_COMMIT"; break;
|
||||
case Dbtc::CS_COMMIT_SENT: out << "CS_COMMIT_SENT"; break;
|
||||
case Dbtc::CS_START_COMMITTING: out << "CS_START_COMMITTING"; break;
|
||||
case Dbtc::CS_COMMITTING: out << "CS_COMMITTING"; break;
|
||||
case Dbtc::CS_REC_COMMITTING: out << "CS_REC_COMMITTING"; break;
|
||||
case Dbtc::CS_WAIT_ABORT_CONF: out << "CS_WAIT_ABORT_CONF"; break;
|
||||
case Dbtc::CS_WAIT_COMPLETE_CONF: out << "CS_WAIT_COMPLETE_CONF"; break;
|
||||
case Dbtc::CS_WAIT_COMMIT_CONF: out << "CS_WAIT_COMMIT_CONF"; break;
|
||||
case Dbtc::CS_FAIL_ABORTING: out << "CS_FAIL_ABORTING"; break;
|
||||
case Dbtc::CS_FAIL_ABORTED: out << "CS_FAIL_ABORTED"; break;
|
||||
case Dbtc::CS_FAIL_PREPARED: out << "CS_FAIL_PREPARED"; break;
|
||||
case Dbtc::CS_FAIL_COMMITTING: out << "CS_FAIL_COMMITTING"; break;
|
||||
case Dbtc::CS_FAIL_COMMITTED: out << "CS_FAIL_COMMITTED"; break;
|
||||
case Dbtc::CS_FAIL_COMPLETED: out << "CS_FAIL_COMPLETED"; break;
|
||||
case Dbtc::CS_START_SCAN: out << "CS_START_SCAN"; break;
|
||||
default:
|
||||
out << "Unknown: " << (int)state; break;
|
||||
}
|
||||
return out;
|
||||
}
|
||||
NdbOut &
|
||||
@ -1240,13 +1269,13 @@ void Dbtc::execTCRELEASEREQ(Signal* signal)
|
||||
jam(); /* JUST REPLY OK */
|
||||
releaseApiCon(signal, apiConnectptr.i);
|
||||
signal->theData[0] = tuserpointer;
|
||||
sendSignal(apiConnectptr.p->ndbapiBlockref,
|
||||
sendSignal(tapiBlockref,
|
||||
GSN_TCRELEASECONF, signal, 1, JBB);
|
||||
} else {
|
||||
jam();
|
||||
signal->theData[0] = tuserpointer;
|
||||
signal->theData[1] = ZINVALID_CONNECTION;
|
||||
sendSignal(apiConnectptr.p->ndbapiBlockref,
|
||||
sendSignal(tapiBlockref,
|
||||
GSN_TCRELEASEREF, signal, 2, JBB);
|
||||
}
|
||||
} else {
|
||||
@ -3683,7 +3712,7 @@ Dbtc::lqhKeyConf_checkTransactionState(Signal * signal,
|
||||
case CS_RECEIVING:
|
||||
if (TnoOfOutStanding == 0) {
|
||||
jam();
|
||||
sendtckeyconf(signal, 0);
|
||||
sendtckeyconf(signal, 2);
|
||||
return;
|
||||
} else {
|
||||
if (apiConnectPtrP->tckeyrec == ZTCOPCONF_SIZE) {
|
||||
@ -3742,7 +3771,7 @@ void Dbtc::sendtckeyconf(Signal* signal, UintR TcommitFlag)
|
||||
ptrAss(localHostptr, hostRecord);
|
||||
UintR TcurrLen = localHostptr.p->noOfWordsTCKEYCONF;
|
||||
UintR confInfo = 0;
|
||||
TcKeyConf::setCommitFlag(confInfo, TcommitFlag);
|
||||
TcKeyConf::setCommitFlag(confInfo, TcommitFlag == 1);
|
||||
TcKeyConf::setMarkerFlag(confInfo, Tmarker);
|
||||
const UintR TpacketLen = 6 + TopWords;
|
||||
regApiPtr->tckeyrec = 0;
|
||||
@ -3767,8 +3796,10 @@ void Dbtc::sendtckeyconf(Signal* signal, UintR TcommitFlag)
|
||||
return; // No queued TcKeyConf
|
||||
}//if
|
||||
}//if
|
||||
|
||||
regApiPtr->m_exec_flag = 0;
|
||||
if(TcommitFlag){
|
||||
jam();
|
||||
regApiPtr->m_exec_flag = 0;
|
||||
}
|
||||
TcKeyConf::setNoOfOperations(confInfo, (TopWords >> 1));
|
||||
if ((TpacketLen > 25) || !is_api){
|
||||
TcKeyConf * const tcKeyConf = (TcKeyConf *)signal->getDataPtrSend();
|
||||
@ -4481,6 +4512,8 @@ void Dbtc::copyApi(Signal* signal)
|
||||
setApiConTimer(tmpApiConnectptr.i, 0, __LINE__);
|
||||
regTmpApiPtr->apiConnectstate = CS_CONNECTED;
|
||||
regTmpApiPtr->commitAckMarker = RNIL;
|
||||
regTmpApiPtr->firstTcConnect = RNIL;
|
||||
regTmpApiPtr->lastTcConnect = RNIL;
|
||||
}//Dbtc::copyApi()
|
||||
|
||||
void Dbtc::unlinkApiConnect(Signal* signal)
|
||||
@ -5003,7 +5036,7 @@ void Dbtc::execLQHKEYREF(Signal* signal)
|
||||
return;
|
||||
} else if (regApiPtr->tckeyrec > 0) {
|
||||
jam();
|
||||
sendtckeyconf(signal, 0);
|
||||
sendtckeyconf(signal, 2);
|
||||
return;
|
||||
}//if
|
||||
}//if
|
||||
@ -5991,7 +6024,9 @@ void Dbtc::timeOutFoundLab(Signal* signal, Uint32 TapiConPtr)
|
||||
/* THIS TRANSACTION HAVE EXPERIENCED A TIME-OUT AND WE NEED TO*/
|
||||
/* FIND OUT WHAT WE NEED TO DO BASED ON THE STATE INFORMATION.*/
|
||||
/*------------------------------------------------------------------*/
|
||||
DEBUG("Time-out in state = " << apiConnectptr.p->apiConnectstate
|
||||
DEBUG("[ H'" << hex << apiConnectptr.p->transid[0]
|
||||
<< " H'" << apiConnectptr.p->transid[1] << "] " << dec
|
||||
<< "Time-out in state = " << apiConnectptr.p->apiConnectstate
|
||||
<< " apiConnectptr.i = " << apiConnectptr.i
|
||||
<< " - exec: " << apiConnectptr.p->m_exec_flag);
|
||||
switch (apiConnectptr.p->apiConnectstate) {
|
||||
@ -8789,6 +8824,10 @@ void Dbtc::releaseScanResources(ScanRecordPtr scanPtr)
|
||||
ndbrequire(scanPtr.p->m_queued_scan_frags.isEmpty());
|
||||
ndbrequire(scanPtr.p->m_delivered_scan_frags.isEmpty());
|
||||
|
||||
|
||||
ndbassert(scanPtr.p->scanApiRec == apiConnectptr.i);
|
||||
ndbassert(apiConnectptr.p->apiScanRec == scanPtr.i);
|
||||
|
||||
// link into free list
|
||||
scanPtr.p->nextScan = cfirstfreeScanrec;
|
||||
scanPtr.p->scanState = ScanRecord::IDLE;
|
||||
@ -8984,6 +9023,10 @@ void Dbtc::scanError(Signal* signal, ScanRecordPtr scanptr, Uint32 errorCode)
|
||||
DEBUG("scanError, errorCode = "<< errorCode <<
|
||||
", scanState = " << scanptr.p->scanState);
|
||||
|
||||
apiConnectptr.i = scanP->scanApiRec;
|
||||
ptrCheckGuard(apiConnectptr, capiConnectFilesize, apiConnectRecord);
|
||||
ndbrequire(apiConnectptr.p->apiScanRec == scanptr.i);
|
||||
|
||||
if(scanP->scanState == ScanRecord::CLOSING_SCAN){
|
||||
jam();
|
||||
close_scan_req_send_conf(signal, scanptr);
|
||||
@ -8992,10 +9035,6 @@ void Dbtc::scanError(Signal* signal, ScanRecordPtr scanptr, Uint32 errorCode)
|
||||
|
||||
ndbrequire(scanP->scanState == ScanRecord::RUNNING);
|
||||
|
||||
apiConnectptr.i = scanP->scanApiRec;
|
||||
ptrCheckGuard(apiConnectptr, capiConnectFilesize, apiConnectRecord);
|
||||
ndbrequire(apiConnectptr.p->apiScanRec == scanptr.i);
|
||||
|
||||
/**
|
||||
* Close scan wo/ having received an order to do so
|
||||
*/
|
||||
@ -9249,7 +9288,9 @@ void Dbtc::execSCAN_NEXTREQ(Signal* signal)
|
||||
|
||||
void
|
||||
Dbtc::close_scan_req(Signal* signal, ScanRecordPtr scanPtr, bool req_received){
|
||||
|
||||
ScanRecord* scanP = scanPtr.p;
|
||||
ndbrequire(scanPtr.p->scanState != ScanRecord::IDLE);
|
||||
scanPtr.p->scanState = ScanRecord::CLOSING_SCAN;
|
||||
scanPtr.p->m_close_scan_req = req_received;
|
||||
|
||||
@ -9990,6 +10031,8 @@ void Dbtc::releaseApiCon(Signal* signal, UintR TapiConnectPtr)
|
||||
cfirstfreeApiConnect = TlocalApiConnectptr.i;
|
||||
setApiConTimer(TlocalApiConnectptr.i, 0, __LINE__);
|
||||
TlocalApiConnectptr.p->apiConnectstate = CS_DISCONNECTED;
|
||||
ndbassert(TlocalApiConnectptr.p->apiScanRec == RNIL);
|
||||
TlocalApiConnectptr.p->ndbapiBlockref = 0;
|
||||
}//Dbtc::releaseApiCon()
|
||||
|
||||
void Dbtc::releaseApiConnectFail(Signal* signal)
|
||||
@ -10042,12 +10085,12 @@ void Dbtc::seizeApiConnect(Signal* signal)
|
||||
apiConnectptr.p->nextApiConnect = RNIL;
|
||||
setApiConTimer(apiConnectptr.i, 0, __LINE__);
|
||||
apiConnectptr.p->apiConnectstate = CS_CONNECTED; /* STATE OF CONNECTION */
|
||||
apiConnectptr.p->triggerPending = false;
|
||||
apiConnectptr.p->isIndexOp = false;
|
||||
} else {
|
||||
jam();
|
||||
terrorCode = ZNO_FREE_API_CONNECTION;
|
||||
}//if
|
||||
apiConnectptr.p->triggerPending = false;
|
||||
apiConnectptr.p->isIndexOp = false;
|
||||
}//Dbtc::seizeApiConnect()
|
||||
|
||||
void Dbtc::seizeApiConnectFail(Signal* signal)
|
||||
@ -10997,11 +11040,15 @@ void Dbtc::sendTcIndxConf(Signal* signal, UintR TcommitFlag)
|
||||
UintR TcurrLen = localHostptr.p->noOfWordsTCINDXCONF;
|
||||
UintR confInfo = 0;
|
||||
TcIndxConf::setNoOfOperations(confInfo, (TopWords >> 1));
|
||||
TcIndxConf::setCommitFlag(confInfo, TcommitFlag);
|
||||
TcIndxConf::setCommitFlag(confInfo, TcommitFlag == 1);
|
||||
TcIndxConf::setMarkerFlag(confInfo, Tmarker);
|
||||
const UintR TpacketLen = 6 + TopWords;
|
||||
regApiPtr->tcindxrec = 0;
|
||||
regApiPtr->m_exec_flag = 0;
|
||||
|
||||
if(TcommitFlag || (regApiPtr->lqhkeyreqrec == regApiPtr->lqhkeyconfrec)){
|
||||
jam();
|
||||
regApiPtr->m_exec_flag = 0;
|
||||
}
|
||||
|
||||
if ((TpacketLen > 25) || !is_api){
|
||||
TcIndxConf * const tcIndxConf = (TcIndxConf *)signal->getDataPtrSend();
|
||||
|
@ -1296,6 +1296,10 @@ NdbConnection::receiveTC_COMMITCONF(const TcCommitConf * commitConf)
|
||||
theCommitStatus = Committed;
|
||||
theCompletionStatus = CompletedSuccess;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
return -1;
|
||||
}//NdbConnection::receiveTC_COMMITCONF()
|
||||
@ -1317,7 +1321,12 @@ NdbConnection::receiveTC_COMMITREF(NdbApiSignal* aSignal)
|
||||
theCommitStatus = Aborted;
|
||||
theCompletionStatus = CompletedFailure;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTC_COMMITREF()
|
||||
|
||||
@ -1336,7 +1345,12 @@ NdbConnection::receiveTCROLLBACKCONF(NdbApiSignal* aSignal)
|
||||
theCommitStatus = Aborted;
|
||||
theCompletionStatus = CompletedSuccess;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCROLLBACKCONF()
|
||||
|
||||
@ -1356,7 +1370,12 @@ NdbConnection::receiveTCROLLBACKREF(NdbApiSignal* aSignal)
|
||||
theCommitStatus = Aborted;
|
||||
theCompletionStatus = CompletedFailure;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCROLLBACKREF()
|
||||
|
||||
@ -1390,7 +1409,12 @@ transactions.
|
||||
theCompletionStatus = CompletedFailure;
|
||||
theCommitStatus = Aborted;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCROLLBACKREP()
|
||||
|
||||
@ -1451,7 +1475,12 @@ from other transactions.
|
||||
return 0; // No more operations to wait for
|
||||
}//if
|
||||
// Not completed the reception yet.
|
||||
}//if
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCKEYCONF()
|
||||
|
||||
@ -1505,6 +1534,10 @@ NdbConnection::receiveTCKEY_FAILCONF(const TcKeyFailConf * failConf)
|
||||
}//while
|
||||
theReleaseOnClose = true;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef VM_TRACE
|
||||
ndbout_c("Recevied TCKEY_FAILCONF wo/ operation");
|
||||
#endif
|
||||
}
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCKEY_FAILCONF()
|
||||
@ -1544,6 +1577,10 @@ NdbConnection::receiveTCKEY_FAILREF(NdbApiSignal* aSignal)
|
||||
theReleaseOnClose = true;
|
||||
theCommitStatus = NdbConnection::Aborted;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef VM_TRACE
|
||||
ndbout_c("Recevied TCKEY_FAILREF wo/ operation");
|
||||
#endif
|
||||
}
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCKEY_FAILREF()
|
||||
@ -1599,7 +1636,12 @@ NdbConnection::receiveTCINDXCONF(const TcIndxConf * indxConf,
|
||||
return 0; // No more operations to wait for
|
||||
}//if
|
||||
// Not completed the reception yet.
|
||||
}//if
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCINDXCONF()
|
||||
|
||||
@ -1628,7 +1670,12 @@ NdbConnection::receiveTCINDXREF( NdbApiSignal* aSignal)
|
||||
theCompletionStatus = NdbConnection::CompletedFailure;
|
||||
theCommitStatus = NdbConnection::Aborted;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}//NdbConnection::receiveTCINDXREF()
|
||||
|
||||
|
@ -69,7 +69,12 @@ NdbConnection::receiveSCAN_TABREF(NdbApiSignal* aSignal){
|
||||
assert(theScanningOp->m_sent_receivers_count);
|
||||
theScanningOp->m_conf_receivers_count++;
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -120,6 +125,10 @@ NdbConnection::receiveSCAN_TABCONF(NdbApiSignal* aSignal,
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
} else {
|
||||
#ifdef NDB_NO_DROPPED_SIGNAL
|
||||
abort();
|
||||
#endif
|
||||
}
|
||||
|
||||
return -1;
|
||||
|
@ -373,8 +373,10 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
switch(tRec->getType()){
|
||||
case NdbReceiver::NDB_OPERATION:
|
||||
case NdbReceiver::NDB_INDEX_OPERATION:
|
||||
if(tCon->OpCompleteSuccess() != -1)
|
||||
if(tCon->OpCompleteSuccess() != -1){
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case NdbReceiver::NDB_SCANRECEIVER:
|
||||
tCon->theScanningOp->receiver_delivered(tRec);
|
||||
@ -392,26 +394,28 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
case GSN_TCKEY_FAILCONF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
|
||||
const TcKeyFailConf * const failConf = (TcKeyFailConf *)tDataPtr;
|
||||
const TcKeyFailConf * failConf = (TcKeyFailConf *)tDataPtr;
|
||||
const BlockReference aTCRef = aSignal->theSendersBlockRef;
|
||||
if (tFirstDataPtr != 0){
|
||||
tOp = void2rec_op(tFirstDataPtr);
|
||||
|
||||
tOp = void2rec_op(tFirstDataPtr);
|
||||
|
||||
if (tOp->checkMagicNumber() == 0) {
|
||||
tCon = tOp->theNdbCon;
|
||||
if (tCon != NULL) {
|
||||
if ((tCon->theSendStatus == NdbConnection::sendTC_OP) ||
|
||||
(tCon->theSendStatus == NdbConnection::sendTC_COMMIT)) {
|
||||
tReturnCode = tCon->receiveTCKEY_FAILCONF(failConf);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
if (tOp->checkMagicNumber(false) == 0) {
|
||||
tCon = tOp->theNdbCon;
|
||||
if (tCon != NULL) {
|
||||
if ((tCon->theSendStatus == NdbConnection::sendTC_OP) ||
|
||||
(tCon->theSendStatus == NdbConnection::sendTC_COMMIT)) {
|
||||
tReturnCode = tCon->receiveTCKEY_FAILCONF(failConf);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
|
||||
}
|
||||
}
|
||||
} else {
|
||||
#ifdef VM_TRACE
|
||||
ndbout_c("Recevied TCKEY_FAILCONF wo/ operation");
|
||||
#endif
|
||||
}
|
||||
if(tFirstData & 1){
|
||||
NdbConnection::sendTC_COMMIT_ACK(theCommitAckSignal,
|
||||
failConf->transId1,
|
||||
@ -423,23 +427,27 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
case GSN_TCKEY_FAILREF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
|
||||
tOp = void2rec_op(tFirstDataPtr);
|
||||
if (tOp->checkMagicNumber() == 0) {
|
||||
tCon = tOp->theNdbCon;
|
||||
if (tCon != NULL) {
|
||||
if ((tCon->theSendStatus == NdbConnection::sendTC_OP) ||
|
||||
(tCon->theSendStatus == NdbConnection::sendTC_ROLLBACK)) {
|
||||
tReturnCode = tCon->receiveTCKEY_FAILREF(aSignal);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
return;
|
||||
if(tFirstDataPtr != 0){
|
||||
tOp = void2rec_op(tFirstDataPtr);
|
||||
if (tOp->checkMagicNumber() == 0) {
|
||||
tCon = tOp->theNdbCon;
|
||||
if (tCon != NULL) {
|
||||
if ((tCon->theSendStatus == NdbConnection::sendTC_OP) ||
|
||||
(tCon->theSendStatus == NdbConnection::sendTC_ROLLBACK)) {
|
||||
tReturnCode = tCon->receiveTCKEY_FAILREF(aSignal);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
}//if
|
||||
} else {
|
||||
#ifdef VM_TRACE
|
||||
ndbout_c("Recevied TCKEY_FAILREF wo/ operation");
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
}
|
||||
case GSN_TCKEYREF:
|
||||
{
|
||||
@ -454,8 +462,9 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
tReturnCode = tOp->receiveTCKEYREF(aSignal);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}//if
|
||||
return;
|
||||
break;
|
||||
}//if
|
||||
}//if
|
||||
} //if
|
||||
@ -501,7 +510,6 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
tReturnCode = tCon->receiveTC_COMMITREF(aSignal);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}//if
|
||||
}//if
|
||||
return;
|
||||
@ -532,7 +540,6 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
tReturnCode = tCon->receiveTCROLLBACKREF(aSignal);
|
||||
if (tReturnCode != -1) {
|
||||
completedTransaction(tCon);
|
||||
return;
|
||||
}//if
|
||||
}//if
|
||||
return;
|
||||
@ -665,66 +672,66 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
|
||||
case GSN_DIHNDBTAMPER:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
|
||||
if (tWaitState != WAIT_NDB_TAMPER)
|
||||
return;
|
||||
tCon = void2con(tFirstDataPtr);
|
||||
if (tCon->checkMagicNumber() != 0)
|
||||
return;
|
||||
tReturnCode = tCon->receiveDIHNDBTAMPER(aSignal);
|
||||
if (tReturnCode != -1)
|
||||
theWaiter.m_state = NO_WAIT;
|
||||
break;
|
||||
}
|
||||
case GSN_SCAN_TABCONF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
assert(tFirstDataPtr);
|
||||
assert(void2con(tFirstDataPtr));
|
||||
assert(void2con(tFirstDataPtr)->checkMagicNumber() == 0);
|
||||
if(tFirstDataPtr &&
|
||||
(tCon = void2con(tFirstDataPtr)) && (tCon->checkMagicNumber() == 0)){
|
||||
|
||||
if(aSignal->m_noOfSections > 0){
|
||||
tReturnCode = tCon->receiveSCAN_TABCONF(aSignal, ptr[0].p, ptr[0].sz);
|
||||
} else {
|
||||
tReturnCode =
|
||||
tCon->receiveSCAN_TABCONF(aSignal,
|
||||
tDataPtr + ScanTabConf::SignalLength,
|
||||
tLen - ScanTabConf::SignalLength);
|
||||
}
|
||||
if (tWaitState != WAIT_NDB_TAMPER)
|
||||
return;
|
||||
tCon = void2con(tFirstDataPtr);
|
||||
if (tCon->checkMagicNumber() != 0)
|
||||
return;
|
||||
tReturnCode = tCon->receiveDIHNDBTAMPER(aSignal);
|
||||
if (tReturnCode != -1)
|
||||
theWaiter.m_state = NO_WAIT;
|
||||
break;
|
||||
} else {
|
||||
}
|
||||
case GSN_SCAN_TABCONF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
assert(tFirstDataPtr);
|
||||
assert(void2con(tFirstDataPtr));
|
||||
assert(void2con(tFirstDataPtr)->checkMagicNumber() == 0);
|
||||
if(tFirstDataPtr &&
|
||||
(tCon = void2con(tFirstDataPtr)) && (tCon->checkMagicNumber() == 0)){
|
||||
|
||||
if(aSignal->m_noOfSections > 0){
|
||||
tReturnCode = tCon->receiveSCAN_TABCONF(aSignal, ptr[0].p, ptr[0].sz);
|
||||
} else {
|
||||
tReturnCode =
|
||||
tCon->receiveSCAN_TABCONF(aSignal,
|
||||
tDataPtr + ScanTabConf::SignalLength,
|
||||
tLen - ScanTabConf::SignalLength);
|
||||
}
|
||||
if (tReturnCode != -1)
|
||||
theWaiter.m_state = NO_WAIT;
|
||||
break;
|
||||
} else {
|
||||
goto InvalidSignal;
|
||||
}
|
||||
}
|
||||
case GSN_SCAN_TABREF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
|
||||
tCon = void2con(tFirstDataPtr);
|
||||
|
||||
assert(tFirstDataPtr != 0 &&
|
||||
void2con(tFirstDataPtr)->checkMagicNumber() == 0);
|
||||
|
||||
if (tCon->checkMagicNumber() == 0){
|
||||
tReturnCode = tCon->receiveSCAN_TABREF(aSignal);
|
||||
if (tReturnCode != -1){
|
||||
theWaiter.m_state = NO_WAIT;
|
||||
}
|
||||
break;
|
||||
}
|
||||
goto InvalidSignal;
|
||||
}
|
||||
}
|
||||
case GSN_SCAN_TABREF:
|
||||
{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
|
||||
tCon = void2con(tFirstDataPtr);
|
||||
|
||||
assert(tFirstDataPtr != 0 &&
|
||||
void2con(tFirstDataPtr)->checkMagicNumber() == 0);
|
||||
|
||||
if (tCon->checkMagicNumber() == 0){
|
||||
tReturnCode = tCon->receiveSCAN_TABREF(aSignal);
|
||||
if (tReturnCode != -1){
|
||||
theWaiter.m_state = NO_WAIT;
|
||||
}
|
||||
break;
|
||||
}
|
||||
goto InvalidSignal;
|
||||
}
|
||||
case GSN_SCAN_TABINFO:
|
||||
{
|
||||
goto InvalidSignal;
|
||||
}
|
||||
{
|
||||
goto InvalidSignal;
|
||||
}
|
||||
case GSN_KEYINFO20: {
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
if (tFirstDataPtr == 0) goto InvalidSignal;
|
||||
@ -777,7 +784,7 @@ Ndb::handleReceivedSignal(NdbApiSignal* aSignal, LinearSectionPtr ptr[3])
|
||||
indxConf->transId2,
|
||||
aTCRef);
|
||||
}
|
||||
break;
|
||||
return;
|
||||
}
|
||||
case GSN_TCINDXREF:{
|
||||
tFirstDataPtr = int2void(tFirstData);
|
||||
@ -940,6 +947,10 @@ Ndb::check_send_timeout()
|
||||
WAITFOR_RESPONSE_TIMEOUT) {
|
||||
#ifdef VM_TRACE
|
||||
a_con->printState();
|
||||
Uint32 t1 = a_con->theTransactionId;
|
||||
Uint32 t2 = a_con->theTransactionId >> 32;
|
||||
ndbout_c("[%.8x %.8x]", t1, t2);
|
||||
abort();
|
||||
#endif
|
||||
a_con->setOperationErrorCodeAbort(4012);
|
||||
a_con->theCommitStatus = NdbConnection::Aborted;
|
||||
|
@ -161,6 +161,11 @@ setSignalLog(){
|
||||
}
|
||||
return false;
|
||||
}
|
||||
#ifdef TRACE_APIREGREQ
|
||||
#define TRACE_GSN(gsn) true
|
||||
#else
|
||||
#define TRACE_GSN(gsn) (gsn != GSN_API_REGREQ && gsn != GSN_API_REGCONF)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// These symbols are needed, but not used in the API
|
||||
@ -168,7 +173,7 @@ int g_sectionSegmentPool;
|
||||
struct ErrorReporter {
|
||||
void handleAssert(const char*, const char*, int);
|
||||
};
|
||||
void ErrorReporter::handleAssert(const char* message, const char* file, int line) {}
|
||||
void ErrorReporter::handleAssert(const char*, const char*, int) {}
|
||||
|
||||
/**
|
||||
* The execute function : Handle received signal
|
||||
@ -183,9 +188,7 @@ execute(void * callbackObj, SignalHeader * const header,
|
||||
Uint32 tRecBlockNo = header->theReceiversBlockNumber;
|
||||
|
||||
#ifdef API_TRACE
|
||||
if(setSignalLog()){
|
||||
// header->theVerId_signalNumber != GSN_API_REGREQ &&
|
||||
// header->theVerId_signalNumber != GSN_API_REGCONF){
|
||||
if(setSignalLog() && TRACE_GSN(header->theVerId_signalNumber)){
|
||||
signalLogger.executeSignal(* header,
|
||||
prio,
|
||||
theData,
|
||||
@ -765,8 +768,7 @@ TransporterFacade::checkForceSend(Uint32 block_number) {
|
||||
|
||||
/******************************************************************************
|
||||
* SEND SIGNAL METHODS
|
||||
******************************************************************************/
|
||||
|
||||
*****************************************************************************/
|
||||
int
|
||||
TransporterFacade::sendSignal(NdbApiSignal * aSignal, NodeId aNode){
|
||||
Uint32* tDataPtr = aSignal->getDataPtrSend();
|
||||
@ -774,9 +776,7 @@ TransporterFacade::sendSignal(NdbApiSignal * aSignal, NodeId aNode){
|
||||
Uint32 TBno = aSignal->theReceiversBlockNumber;
|
||||
if(getIsNodeSendable(aNode) == true){
|
||||
#ifdef API_TRACE
|
||||
if(setSignalLog()){
|
||||
// aSignal->theVerId_signalNumber != GSN_API_REGREQ &&
|
||||
// aSignal->theVerId_signalNumber != GSN_API_REGCONF){
|
||||
if(setSignalLog() && TRACE_GSN(aSignal->theVerId_signalNumber)){
|
||||
Uint32 tmp = aSignal->theSendersBlockRef;
|
||||
aSignal->theSendersBlockRef = numberToRef(tmp, theOwnId);
|
||||
LinearSectionPtr ptr[3];
|
||||
@ -810,9 +810,7 @@ TransporterFacade::sendSignal(NdbApiSignal * aSignal, NodeId aNode){
|
||||
int
|
||||
TransporterFacade::sendSignalUnCond(NdbApiSignal * aSignal, NodeId aNode){
|
||||
#ifdef API_TRACE
|
||||
if(setSignalLog()){
|
||||
//aSignal->theVerId_signalNumber != GSN_API_REGREQ &&
|
||||
//aSignal->theVerId_signalNumber != GSN_API_REGCONF
|
||||
if(setSignalLog() && TRACE_GSN(aSignal->theVerId_signalNumber)){
|
||||
Uint32 tmp = aSignal->theSendersBlockRef;
|
||||
aSignal->theSendersBlockRef = numberToRef(tmp, theOwnId);
|
||||
LinearSectionPtr ptr[3];
|
||||
@ -842,7 +840,7 @@ TransporterFacade::sendFragmentedSignal(NdbApiSignal* aSignal, NodeId aNode,
|
||||
aSignal->m_noOfSections = secs;
|
||||
if(getIsNodeSendable(aNode) == true){
|
||||
#ifdef API_TRACE
|
||||
if(setSignalLog()){
|
||||
if(setSignalLog() && TRACE_GSN(aSignal->theVerId_signalNumber)){
|
||||
Uint32 tmp = aSignal->theSendersBlockRef;
|
||||
aSignal->theSendersBlockRef = numberToRef(tmp, theOwnId);
|
||||
signalLogger.sendSignal(* aSignal,
|
||||
@ -878,7 +876,7 @@ TransporterFacade::sendFragmentedSignalUnCond(NdbApiSignal* aSignal,
|
||||
aSignal->m_noOfSections = secs;
|
||||
|
||||
#ifdef API_TRACE
|
||||
if(setSignalLog()){
|
||||
if(setSignalLog() && TRACE_GSN(aSignal->theVerId_signalNumber)){
|
||||
Uint32 tmp = aSignal->theSendersBlockRef;
|
||||
aSignal->theSendersBlockRef = numberToRef(tmp, theOwnId);
|
||||
signalLogger.sendSignal(* aSignal,
|
||||
|
@ -63,6 +63,8 @@ public:
|
||||
bool getPropertyWait(const char*, Uint32);
|
||||
const char* getPropertyWait(const char*, const char* );
|
||||
|
||||
void decProperty(const char *);
|
||||
|
||||
// Communicate with other tests
|
||||
void stopTest();
|
||||
bool isTestStopped();
|
||||
|
@ -380,6 +380,25 @@ runVerifyIndex(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_OK;
|
||||
}
|
||||
|
||||
int
|
||||
sync_down(NDBT_Context* ctx){
|
||||
Uint32 threads = ctx->getProperty("PauseThreads", (unsigned)0);
|
||||
if(threads){
|
||||
ctx->decProperty("PauseThreads");
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
sync_up_and_wait(NDBT_Context* ctx){
|
||||
Uint32 threads = ctx->getProperty("Threads", (unsigned)0);
|
||||
ndbout_c("Setting PauseThreads to %d", threads);
|
||||
ctx->setProperty("PauseThreads", threads);
|
||||
ctx->getPropertyWait("PauseThreads", (unsigned)0);
|
||||
if(threads){
|
||||
ndbout_c("wait completed");
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
runTransactions1(NDBT_Context* ctx, NDBT_Step* step){
|
||||
// Verify that data in index match
|
||||
@ -394,10 +413,17 @@ runTransactions1(NDBT_Context* ctx, NDBT_Step* step){
|
||||
g_err << "Updated table failed" << endl;
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
if (hugoTrans.scanUpdateRecords(pNdb, rows, batchSize) != 0){
|
||||
g_err << "Updated table failed" << endl;
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
}
|
||||
return NDBT_OK;
|
||||
}
|
||||
@ -418,7 +444,7 @@ runTransactions2(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
#endif
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
#if 1
|
||||
@ -427,6 +453,7 @@ runTransactions2(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
#endif
|
||||
sync_down(ctx);
|
||||
}
|
||||
return NDBT_OK;
|
||||
}
|
||||
@ -447,6 +474,7 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
g_err << "Load table failed" << endl;
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
@ -455,6 +483,7 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
@ -463,6 +492,7 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
@ -471,6 +501,7 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
@ -479,6 +510,7 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
@ -486,12 +518,15 @@ runTransactions3(NDBT_Context* ctx, NDBT_Step* step){
|
||||
g_err << "Clear table failed" << endl;
|
||||
return NDBT_FAILED;
|
||||
}
|
||||
|
||||
sync_down(ctx);
|
||||
if(ctx->isTestStopped())
|
||||
break;
|
||||
|
||||
int count = -1;
|
||||
if(utilTrans.selectCount(pNdb, 64, &count) != 0 || count != 0)
|
||||
return NDBT_FAILED;
|
||||
sync_down(ctx);
|
||||
}
|
||||
return NDBT_OK;
|
||||
}
|
||||
@ -510,6 +545,7 @@ int runRestarts(NDBT_Context* ctx, NDBT_Step* step){
|
||||
result = NDBT_FAILED;
|
||||
break;
|
||||
}
|
||||
sync_up_and_wait(ctx);
|
||||
i++;
|
||||
}
|
||||
ctx->stopTest();
|
||||
@ -1259,6 +1295,7 @@ TESTCASE("CreateLoadDrop_O",
|
||||
TESTCASE("NFNR1",
|
||||
"Test that indexes are correctly maintained during node fail and node restart"){
|
||||
TC_PROPERTY("LoggedIndexes", (unsigned)0);
|
||||
//TC_PROPERTY("Threads", 2);
|
||||
INITIALIZER(runClearTable);
|
||||
INITIALIZER(createRandomIndex);
|
||||
INITIALIZER(runLoadTable);
|
||||
|
@ -132,6 +132,17 @@ void NDBT_Context::setProperty(const char* _name, Uint32 _val){
|
||||
assert(b == true);
|
||||
NdbMutex_Unlock(propertyMutexPtr);
|
||||
}
|
||||
void
|
||||
NDBT_Context::decProperty(const char * name){
|
||||
NdbMutex_Lock(propertyMutexPtr);
|
||||
Uint32 val = 0;
|
||||
if(props.get(name, &val)){
|
||||
assert(val > 0);
|
||||
props.put(name, (val - 1), true);
|
||||
}
|
||||
NdbCondition_Broadcast(propertyCondPtr);
|
||||
NdbMutex_Unlock(propertyMutexPtr);
|
||||
}
|
||||
|
||||
void NDBT_Context::setProperty(const char* _name, const char* _val){
|
||||
NdbMutex_Lock(propertyMutexPtr);
|
||||
@ -994,6 +1005,7 @@ int NDBT_TestSuite::execute(int argc, const char** argv){
|
||||
res = executeAll(_testname);
|
||||
} else {
|
||||
testSuiteTimer.doStart();
|
||||
Ndb ndb("TEST_DB"); ndb.init();
|
||||
for(int i = optind; i<argc; i++){
|
||||
executeOne(argv[i], _testname);
|
||||
}
|
||||
|
Reference in New Issue
Block a user