summaryrefslogtreecommitdiff
path: root/ndb/src/ndbapi/NdbOperationScan.cpp
diff options
context:
space:
mode:
authorunknown <joreland@mysql.com>2004-05-26 13:24:14 +0200
committerunknown <joreland@mysql.com>2004-05-26 13:24:14 +0200
commit934b303359c8cb6a0ddc2eae268900a23b5c6374 (patch)
tree0280375c810eb97bcc0397cfd3872e453d350683 /ndb/src/ndbapi/NdbOperationScan.cpp
parentd93d48c11ba2012b351547e8ff2c583c9c18e4f3 (diff)
downloadmariadb-git-934b303359c8cb6a0ddc2eae268900a23b5c6374.tar.gz
wl1671 - Sorted scan
Diffstat (limited to 'ndb/src/ndbapi/NdbOperationScan.cpp')
-rw-r--r--ndb/src/ndbapi/NdbOperationScan.cpp560
1 files changed, 0 insertions, 560 deletions
diff --git a/ndb/src/ndbapi/NdbOperationScan.cpp b/ndb/src/ndbapi/NdbOperationScan.cpp
index df4f2421ec0..283eb591bdb 100644
--- a/ndb/src/ndbapi/NdbOperationScan.cpp
+++ b/ndb/src/ndbapi/NdbOperationScan.cpp
@@ -14,563 +14,3 @@
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
-#include "NdbOperation.hpp"
-#include "NdbScanReceiver.hpp"
-
-#include <signaldata/TcKeyReq.hpp>
-#include <signaldata/ScanTab.hpp>
-#include <signaldata/ScanFrag.hpp>
-#include <signaldata/KeyInfo.hpp>
-
-
-/******************************************************************************
- * int openScanRead();
- *****************************************************************************/
-int
-NdbOperation::openScanRead(Uint32 aParallelism)
-{
- aParallelism = checkParallelism(aParallelism);
-
- if ((theNdbCon->theCommitStatus != Started) &&
- (theStatus != Init) &&
- (aParallelism == 0)) {
- setErrorCode(4200);
- return -1;
- }
- return openScan(aParallelism, false, false, false);
-}
-
-/****************************************************************************
- * int openScanExclusive();
- ****************************************************************************/
-int
-NdbOperation::openScanExclusive(Uint32 aParallelism)
-{
- aParallelism = checkParallelism(aParallelism);
-
- if ((theNdbCon->theCommitStatus != Started) &&
- (theStatus != Init) &&
- (aParallelism == 0)) {
- setErrorCode(4200);
- return -1;
- }
- return openScan(aParallelism, true, true, false);
-}
-
-/******************************************************************************
- * int openScanReadHoldLock();
- *****************************************************************************/
-int
-NdbOperation::openScanReadHoldLock(Uint32 aParallelism)
-{
- aParallelism = checkParallelism(aParallelism);
-
- if ((theNdbCon->theCommitStatus != Started) &&
- (theStatus != Init) &&
- (aParallelism == 0)) {
- setErrorCode(4200);
- return -1;
- }
- return openScan(aParallelism, false, true, false);
-}
-
-/******************************************************************************
- * int openScanReadCommitted();
- *****************************************************************************/
-int
-NdbOperation::openScanReadCommitted(Uint32 aParallelism)
-{
- aParallelism = checkParallelism(aParallelism);
-
- if ((theNdbCon->theCommitStatus != Started) &&
- (theStatus != Init) &&
- (aParallelism == 0)) {
- setErrorCode(4200);
- return -1;
- }
- return openScan(aParallelism, false, false, true);
-}
-
-/****************************************************************************
- * int checkParallelism();
- * Remark If the parallelism is set wrong the number of scan-operations
- * will not correspond to the number of TRANSID_AI signals returned
- * from NDB and the result will be a crash, therefore
- * we adjust it or return an error if the value is totally wrong.
- ****************************************************************************/
-int
-NdbOperation::checkParallelism(Uint32 aParallelism)
-{
- if (aParallelism == 0) {
- setErrorCodeAbort(4232);
- return 0;
- }
- if (aParallelism > 16) {
- if (aParallelism <= 240) {
-
- /**
- * If tscanConcurrency > 16 it must be a multiple of 16
- */
- if (((aParallelism >> 4) << 4) < aParallelism) {
- aParallelism = ((aParallelism >> 4) << 4) + 16;
- }//if
-
- /*---------------------------------------------------------------*/
- /* We cannot have a parallelism > 16 per node */
- /*---------------------------------------------------------------*/
- if ((aParallelism / theNdb->theNoOfDBnodes) > 16) {
- aParallelism = theNdb->theNoOfDBnodes * 16;
- }//if
-
- } else {
- setErrorCodeAbort(4232);
- aParallelism = 0;
- }//if
- }//if
- return aParallelism;
-}//NdbOperation::checkParallelism()
-
-/**********************************************************************
- * int openScan();
- *************************************************************************/
-int
-NdbOperation::openScan(Uint32 aParallelism,
- bool lockMode, bool lockHoldMode, bool readCommitted)
-{
- aParallelism = checkParallelism(aParallelism);
- if(aParallelism == 0){
- return 0;
- }
- NdbScanReceiver* tScanRec;
- // It is only possible to call openScan if
- // 1. this transcation don't already contain another scan operation
- // 2. this transaction don't already contain other operations
- // 3. theScanOp contains a NdbScanOperation
- if (theNdbCon->theScanningOp != NULL){
- setErrorCode(4605);
- return -1;
- }
-
- if ((theNdbCon->theFirstOpInList != this) ||
- (theNdbCon->theLastOpInList != this)) {
- setErrorCode(4603);
- return -1;
- }
- theNdbCon->theScanningOp = this;
-
- initScan();
- theParallelism = aParallelism;
-
- // If the scan is on ordered index then it is a range scan
- if (m_currentTable->m_indexType == NdbDictionary::Index::OrderedIndex ||
- m_currentTable->m_indexType == NdbDictionary::Index::UniqueOrderedIndex) {
- assert(m_currentTable == m_accessTable);
- m_currentTable = theNdb->theDictionary->getTable(m_currentTable->m_primaryTable.c_str());
- assert(m_currentTable != NULL);
- // Modify operation state
- theStatus = SetBound;
- theOperationType = OpenRangeScanRequest;
- }
-
- theScanReceiversArray = new NdbScanReceiver* [aParallelism];
- if (theScanReceiversArray == NULL){
- setErrorCodeAbort(4000);
- return -1;
- }
-
- for (Uint32 i = 0; i < aParallelism; i ++) {
- tScanRec = theNdb->getNdbScanRec();
- if (tScanRec == NULL) {
- setErrorCodeAbort(4000);
- return -1;
- }//if
- tScanRec->init(this, lockMode);
- theScanReceiversArray[i] = tScanRec;
- }
-
- theSCAN_TABREQ = theNdb->getSignal();
- if (theSCAN_TABREQ == NULL) {
- setErrorCodeAbort(4000);
- return -1;
- }//if
- ScanTabReq * const scanTabReq = CAST_PTR(ScanTabReq, theSCAN_TABREQ->getDataPtrSend());
- scanTabReq->apiConnectPtr = theNdbCon->theTCConPtr;
- scanTabReq->tableId = m_accessTable->m_tableId;
- scanTabReq->tableSchemaVersion = m_accessTable->m_version;
- scanTabReq->storedProcId = 0xFFFF;
- scanTabReq->buddyConPtr = theNdbCon->theBuddyConPtr;
-
- Uint32 reqInfo = 0;
- ScanTabReq::setParallelism(reqInfo, aParallelism);
- ScanTabReq::setLockMode(reqInfo, lockMode);
- ScanTabReq::setHoldLockFlag(reqInfo, lockHoldMode);
- ScanTabReq::setReadCommittedFlag(reqInfo, readCommitted);
- if (theOperationType == OpenRangeScanRequest)
- ScanTabReq::setRangeScanFlag(reqInfo, true);
- scanTabReq->requestInfo = reqInfo;
-
- Uint64 transId = theNdbCon->getTransactionId();
- scanTabReq->transId1 = (Uint32) transId;
- scanTabReq->transId2 = (Uint32) (transId >> 32);
-
- for (Uint32 i = 0; i < 16 && i < aParallelism ; i++) {
- scanTabReq->apiOperationPtr[i] = theScanReceiversArray[i]->ptr2int();
- }//for
-
- // Create one additional SCAN_TABINFO for each
- // 16 of parallelism
- NdbApiSignal* tSignal;
- Uint32 tParallelism = aParallelism;
- while (tParallelism > 16) {
- tSignal = theNdb->getSignal();
- if (tSignal == NULL) {
- setErrorCodeAbort(4000);
- return -1;
- }//if
- if (tSignal->setSignal(GSN_SCAN_TABINFO) == -1) {
- setErrorCode(4001);
- return -1;
- }
- tSignal->next(theFirstSCAN_TABINFO_Send);
- theFirstSCAN_TABINFO_Send = tSignal;
- tParallelism -= 16;
- }//while
-
- // Format all SCAN_TABINFO signals
- tParallelism = 16;
- tSignal = theFirstSCAN_TABINFO_Send;
- while (tSignal != NULL) {
- tSignal->setData(theNdbCon->theTCConPtr, 1);
- for (int i = 0; i < 16 ; i++) {
- tSignal->setData(theScanReceiversArray[i + tParallelism]->ptr2int(), i + 2);
- }//for
- tSignal = tSignal->next();
- tParallelism += 16;
- }//while
-
- getFirstATTRINFOScan();
- return 0;
-}//NdbScanOperation::openScan()
-
-/*****************************************************************************
- * int getFirstATTRINFOScan( U_int32 aData )
- *
- * Return Value: Return 0: Successful
- * Return -1: All other cases
- * Parameters: None: Only allocate the first signal.
- * Remark: When a scan is defined we need to use this method instead
- * of insertATTRINFO for the first signal.
- * This is because we need not to mess up the code in
- * insertATTRINFO with if statements since we are not
- * interested in the TCKEYREQ signal.
- *****************************************************************************/
-int
-NdbOperation::getFirstATTRINFOScan()
-{
- NdbApiSignal* tSignal;
-
- tSignal = theNdb->getSignal();
- if (tSignal == NULL){
- setErrorCodeAbort(4000);
- return -1;
- }
- tSignal->setSignal(m_attrInfoGSN);
- theAI_LenInCurrAI = 8;
- theATTRINFOptr = &tSignal->getDataPtrSend()[8];
- theFirstATTRINFO = tSignal;
- theCurrentATTRINFO = tSignal;
- theCurrentATTRINFO->next(NULL);
- return 0;
-}
-
-/*
- * After setBound() are done, move the accumulated ATTRINFO signals to
- * a separate list. Then continue with normal scan.
- */
-int
-NdbOperation::saveBoundATTRINFO()
-{
- theCurrentATTRINFO->setLength(theAI_LenInCurrAI);
- theBoundATTRINFO = theFirstATTRINFO;
- theTotalBoundAI_Len = theTotalCurrAI_Len;
- theTotalCurrAI_Len = 5;
- theBoundATTRINFO->setData(theTotalBoundAI_Len, 4);
- theBoundATTRINFO->setData(0, 5);
- theBoundATTRINFO->setData(0, 6);
- theBoundATTRINFO->setData(0, 7);
- theBoundATTRINFO->setData(0, 8);
- theStatus = GetValue;
- return getFirstATTRINFOScan();
-}
-
-/*****************************************************************************
- * void releaseScan()
- *
- * Return Value No return value.
- * Parameters: No parameters.
- * Remark: Release objects after scanning.
- *****************************************************************************/
-void
-NdbOperation::releaseScan()
-{
- NdbScanReceiver* tScanRec;
- TransporterFacade::instance()->lock_mutex();
- for (Uint32 i = 0; i < theParallelism && theScanReceiversArray != NULL; i++) {
- tScanRec = theScanReceiversArray[i];
- if (tScanRec != NULL) {
- tScanRec->release();
- tScanRec->next(NULL);
- }
- }
- TransporterFacade::instance()->unlock_mutex();
- releaseSignals();
-
- if (theScanReceiversArray != NULL) {
- for (Uint32 i = 0; i < theParallelism; i++) {
- NdbScanReceiver* tScanRec;
- tScanRec = theScanReceiversArray[i];
- if (tScanRec != NULL) {
- theNdb->releaseNdbScanRec(tScanRec);
- theScanReceiversArray[i] = NULL;
- }
- }
-
- delete [] theScanReceiversArray;
- }//if
- theScanReceiversArray = NULL;
-
- if (theSCAN_TABREQ != NULL){
- theNdb->releaseSignal(theSCAN_TABREQ);
- theSCAN_TABREQ = NULL;
- }
-}
-
-void NdbOperation::releaseSignals(){
- theNdb->releaseSignalsInList(&theFirstSCAN_TABINFO_Send);
- theFirstSCAN_TABINFO_Send = NULL;
- theLastSCAN_TABINFO_Send = NULL;
- // theNdb->releaseSignalsInList(&theFirstSCAN_TABINFO_Recv);
-
- while(theFirstSCAN_TABINFO_Recv != NULL){
- NdbApiSignal* tmp = theFirstSCAN_TABINFO_Recv;
- theFirstSCAN_TABINFO_Recv = tmp->next();
- delete tmp;
- }
- theFirstSCAN_TABINFO_Recv = NULL;
- theLastSCAN_TABINFO_Recv = NULL;
- if (theSCAN_TABCONF_Recv != NULL){
- // theNdb->releaseSignal(theSCAN_TABCONF_Recv);
- delete theSCAN_TABCONF_Recv;
- theSCAN_TABCONF_Recv = NULL;
- }
-}
-
-
-void NdbOperation::prepareNextScanResult(){
- NdbScanReceiver* tScanRec;
- for (Uint32 i = 0; i < theParallelism; i++) {
- tScanRec = theScanReceiversArray[i];
- assert(tScanRec != NULL);
- tScanRec->prepareNextScanResult();
- tScanRec->next(NULL);
- }
- releaseSignals();
-}
-
-/******************************************************************************
- * void initScan();
- *
- * Return Value: Return 0 : init was successful.
- * Return -1: In all other case.
- * Remark: Initiates operation record after allocation.
- *****************************************************************************/
-void
-NdbOperation::initScan()
-{
- theTotalRecAI_Len = 0;
- theCurrRecAI_Len = 0;
- theStatus = GetValue;
- theOperationType = OpenScanRequest;
- theCurrentRecAttr = theFirstRecAttr;
- theScanInfo = 0;
- theMagicNumber = 0xABCDEF01;
- theTotalCurrAI_Len = 5;
-
- theFirstLabel = NULL;
- theLastLabel = NULL;
- theFirstBranch = NULL;
- theLastBranch = NULL;
-
- theFirstCall = NULL;
- theLastCall = NULL;
- theFirstSubroutine = NULL;
- theLastSubroutine = NULL;
-
- theNoOfLabels = 0;
- theNoOfSubroutines = 0;
-
- theSubroutineSize = 0;
- theInitialReadSize = 0;
- theInterpretedSize = 0;
- theFinalUpdateSize = 0;
- theFinalReadSize = 0;
- theInterpretIndicator = 1;
-
-
- theFirstSCAN_TABINFO_Send = NULL;
- theLastSCAN_TABINFO_Send = NULL;
- theFirstSCAN_TABINFO_Recv = NULL;
- theLastSCAN_TABINFO_Recv = NULL;
- theSCAN_TABCONF_Recv = NULL;
-
- theScanReceiversArray = NULL;
-
- theTotalBoundAI_Len = 0;
- theBoundATTRINFO = NULL;
- return;
-}
-
-NdbOperation* NdbOperation::takeOverForDelete(NdbConnection* updateTrans){
- return takeOverScanOp(DeleteRequest, updateTrans);
-}
-
-NdbOperation* NdbOperation::takeOverForUpdate(NdbConnection* updateTrans){
- return takeOverScanOp(UpdateRequest, updateTrans);
-}
-/******************************************************************************
- * NdbOperation* takeOverScanOp(NdbConnection* updateTrans);
- *
- * Parameters: The update transactions NdbConnection pointer.
- * Return Value: A reference to the transferred operation object
- * or NULL if no success.
- * Remark: Take over the scanning transactions NdbOperation
- * object for a tuple to an update transaction,
- * which is the last operation read in nextScanResult()
- * (theNdbCon->thePreviousScanRec)
- *
- * FUTURE IMPLEMENTATION: (This note was moved from header file.)
- * In the future, it will even be possible to transfer
- * to a NdbConnection on another Ndb-object.
- * In this case the receiving NdbConnection-object must call
- * a method receiveOpFromScan to actually receive the information.
- * This means that the updating transactions can be placed
- * in separate threads and thus increasing the parallelism during
- * the scan process.
- *****************************************************************************/
-NdbOperation*
-NdbOperation::takeOverScanOp(OperationType opType, NdbConnection* updateTrans)
-{
- if (opType != UpdateRequest && opType != DeleteRequest) {
- setErrorCode(4604);
- return NULL;
- }
-
- const NdbScanReceiver* tScanRec = theNdbCon->thePreviousScanRec;
- if (tScanRec == NULL){
- // No operation read by nextScanResult
- setErrorCode(4609);
- return NULL;
- }
-
- if (tScanRec->theFirstKEYINFO20_Recv == NULL){
- // No KEYINFO20 received
- setErrorCode(4608);
- return NULL;
- }
-
- NdbOperation * newOp = updateTrans->getNdbOperation(m_currentTable);
- if (newOp == NULL){
- return NULL;
- }
-
- /**
- * Copy and caclulate attributes from the scanned operation to the
- * new operation
- */
- const KeyInfo20 * const firstKeyInfo20 =
- CAST_CONSTPTR(KeyInfo20, tScanRec->theFirstKEYINFO20_Recv->getDataPtr());
- const Uint32 totalKeyLen = firstKeyInfo20->keyLen;
- newOp->theTupKeyLen = totalKeyLen;
-
- newOp->theOperationType = opType;
- if (opType == DeleteRequest) {
- newOp->theStatus = GetValue;
- } else {
- newOp->theStatus = SetValue;
- }
- const Uint32 tScanInfo = firstKeyInfo20->scanInfo_Node & 0xFFFF;
- const Uint32 tTakeOverNode = firstKeyInfo20->scanInfo_Node >> 16;
- {
- UintR scanInfo = 0;
- TcKeyReq::setTakeOverScanFlag(scanInfo, 1);
- TcKeyReq::setTakeOverScanNode(scanInfo, tTakeOverNode);
- TcKeyReq::setTakeOverScanInfo(scanInfo, tScanInfo);
- newOp->theScanInfo = scanInfo;
- }
-
- /**
- * Copy received KEYINFO20 signals into TCKEYREQ and KEYINFO signals
- * put them in list of the new op
- */
- TcKeyReq * const tcKeyReq =
- CAST_PTR(TcKeyReq, newOp->theTCREQ->getDataPtrSend());
-
- // Copy the first 8 words of key info from KEYINF20 into TCKEYREQ
- for (Uint32 i = 0; i < TcKeyReq::MaxKeyInfo; i++) {
- tcKeyReq->keyInfo[i] = firstKeyInfo20->keyData[i];
- }
- if (totalKeyLen > TcKeyReq::MaxKeyInfo) {
-
- Uint32 keyWordsCopied = TcKeyReq::MaxKeyInfo;
-
- // Create KEYINFO signals in newOp
- for (Uint32 i = keyWordsCopied; i < totalKeyLen; i += KeyInfo::DataLength){
- NdbApiSignal* tSignal = theNdb->getSignal();
- if (tSignal == NULL){
- setErrorCodeAbort(4000);
- return NULL;
- }
- if (tSignal->setSignal(GSN_KEYINFO) == -1){
- setErrorCodeAbort(4001);
- return NULL;
- }
- tSignal->next(newOp->theFirstKEYINFO);
- newOp->theFirstKEYINFO = tSignal;
- }
-
- // Init pointers to KEYINFO20 signal
- NdbApiSignal* currKeyInfo20 = tScanRec->theFirstKEYINFO20_Recv;
- const KeyInfo20 * keyInfo20 =
- CAST_CONSTPTR(KeyInfo20, currKeyInfo20->getDataPtr());
- Uint32 posInKeyInfo20 = keyWordsCopied;
-
- // Init pointers to KEYINFO signal
- NdbApiSignal* currKeyInfo = newOp->theFirstKEYINFO;
- KeyInfo * keyInfo = CAST_PTR(KeyInfo, currKeyInfo->getDataPtrSend());
- Uint32 posInKeyInfo = 0;
-
- // Copy from KEYINFO20 to KEYINFO
- while(keyWordsCopied < totalKeyLen){
- keyInfo->keyData[posInKeyInfo++] = keyInfo20->keyData[posInKeyInfo20++];
- keyWordsCopied++;
- if(keyWordsCopied >= totalKeyLen)
- break;
- if (posInKeyInfo20 >=
- (currKeyInfo20->getLength()-KeyInfo20::HeaderLength)){
- currKeyInfo20 = currKeyInfo20->next();
- keyInfo20 = CAST_CONSTPTR(KeyInfo20, currKeyInfo20->getDataPtr());
- posInKeyInfo20 = 0;
- }
- if (posInKeyInfo >= KeyInfo::DataLength){
- currKeyInfo = currKeyInfo->next();
- keyInfo = CAST_PTR(KeyInfo, currKeyInfo->getDataPtrSend());
- posInKeyInfo = 0;
- }
- }
- }
-
- return newOp;
-}
-
-
-