3600 Maitrayi Sabaratnam 2012-03-15
SPJ: handling dupsection failures
modified:
storage/ndb/src/kernel/blocks/dbspj/DbspjMain.cpp
storage/ndb/test/ndbapi/testSpj.cpp
3599 Ole John Aske 2012-03-12
Fixed some incorrectly indented lines in SPJ block
modified:
storage/ndb/src/kernel/blocks/dbspj/DbspjMain.cpp
=== modified file 'storage/ndb/src/kernel/blocks/dbspj/DbspjMain.cpp'
--- a/storage/ndb/src/kernel/blocks/dbspj/DbspjMain.cpp 2012-03-12 09:33:06 +0000
+++ b/storage/ndb/src/kernel/blocks/dbspj/DbspjMain.cpp 2012-03-15 14:33:38 +0000
@@ -3059,145 +3059,192 @@ Dbspj::lookup_send(Signal* signal,
Uint32 keyInfoPtrI = treeNodePtr.p->m_send.m_keyInfoPtrI;
Uint32 attrInfoPtrI = treeNodePtr.p->m_send.m_attrInfoPtrI;
- if (treeNodePtr.p->m_bits & TreeNode::T_ONE_SHOT)
- {
- jam();
- /**
- * Pass sections to send
- */
- treeNodePtr.p->m_send.m_attrInfoPtrI = RNIL;
- treeNodePtr.p->m_send.m_keyInfoPtrI = RNIL;
- }
- else
+ Uint32 err = 0;
+
+ do
{
- if ((treeNodePtr.p->m_bits & TreeNode::T_KEYINFO_CONSTRUCTED) == 0)
+ if (treeNodePtr.p->m_bits & TreeNode::T_ONE_SHOT)
{
jam();
- Uint32 tmp = RNIL;
- ndbrequire(dupSection(tmp, keyInfoPtrI)); // TODO handle error
- keyInfoPtrI = tmp;
+ /**
+ * Pass sections to send
+ */
+ treeNodePtr.p->m_send.m_attrInfoPtrI = RNIL;
+ treeNodePtr.p->m_send.m_keyInfoPtrI = RNIL;
}
else
{
- jam();
- treeNodePtr.p->m_send.m_keyInfoPtrI = RNIL;
+ if ((treeNodePtr.p->m_bits & TreeNode::T_KEYINFO_CONSTRUCTED) == 0)
+ {
+ jam();
+ Uint32 tmp = RNIL;
+ if (!dupSection(tmp, keyInfoPtrI))
+ {
+ jam();
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ keyInfoPtrI = tmp;
+ }
+ else
+ {
+ jam();
+ treeNodePtr.p->m_send.m_keyInfoPtrI = RNIL;
+ }
+
+ if ((treeNodePtr.p->m_bits & TreeNode::T_ATTRINFO_CONSTRUCTED) == 0)
+ {
+ jam();
+ Uint32 tmp = RNIL;
+
+ /**
+ * Test execution terminated due to 'OutOfSectionMemory' which
+ * may happen for different treeNodes in the request:
+ * - 17070: Fail on any lookup_send()
+ * - 17071: Fail on lookup_send() if 'isLeaf'
+ * - 17072: Fail on lookup_send() if treeNode not root
+ */
+
+ if (ERROR_INSERTED_CLEAR(17070) ||
+ (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17071)) ||
+ (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17072)))
+ {
+ jam();
+ ndbout_c("Injecting OutOfSectionMemory error at line %d file %s",
+ __LINE__, __FILE__);
+ if (keyInfoPtrI != RNIL)
+ releaseSection(keyInfoPtrI);
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ if (!dupSection(tmp, attrInfoPtrI))
+ {
+ jam();
+ if (keyInfoPtrI != RNIL)
+ releaseSection(keyInfoPtrI);
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ attrInfoPtrI = tmp;
+ }
+ else
+ {
+ jam();
+ treeNodePtr.p->m_send.m_attrInfoPtrI = RNIL;
+ }
}
- if ((treeNodePtr.p->m_bits & TreeNode::T_ATTRINFO_CONSTRUCTED) == 0)
+ getSection(handle.m_ptr[0], keyInfoPtrI);
+ getSection(handle.m_ptr[1], attrInfoPtrI);
+ handle.m_cnt = 2;
+
+ /**
+ * Inject error to test LQHKEYREF handling:
+ * Tampering with tableSchemaVersion such that LQH will
+ * return LQHKEYREF('1227: Invalid schema version')
+ * May happen for different treeNodes in the request:
+ * - 17030: Fail on any lookup_send()
+ * - 17031: Fail on lookup_send() if 'isLeaf'
+ * - 17032: Fail on lookup_send() if treeNode not root
+ */
+ if (ERROR_INSERTED_CLEAR(17030) ||
+ (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17031)) ||
+ (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17032)))
{
jam();
- Uint32 tmp = RNIL;
- ndbrequire(dupSection(tmp, attrInfoPtrI)); // TODO handle error
- attrInfoPtrI = tmp;
+ req->tableSchemaVersion += (1 << 16); // Provoke 'Invalid schema version'
+ }
+
+#if defined DEBUG_LQHKEYREQ
+ ndbout_c("LQHKEYREQ to %x", ref);
+ printLQHKEYREQ(stdout, signal->getDataPtrSend(),
+ NDB_ARRAY_SIZE(treeNodePtr.p->m_lookup_data.m_lqhKeyReq),
+ DBLQH);
+ printf("KEYINFO: ");
+ print(handle.m_ptr[0], stdout);
+ printf("ATTRINFO: ");
+ print(handle.m_ptr[1], stdout);
+#endif
+
+ Uint32 Tnode = refToNode(ref);
+ if (Tnode == getOwnNodeId())
+ {
+ c_Counters.incr_counter(CI_LOCAL_READS_SENT, 1);
}
else
{
- jam();
- treeNodePtr.p->m_send.m_attrInfoPtrI = RNIL;
+ c_Counters.incr_counter(CI_REMOTE_READS_SENT, 1);
}
- }
-
- getSection(handle.m_ptr[0], keyInfoPtrI);
- getSection(handle.m_ptr[1], attrInfoPtrI);
- handle.m_cnt = 2;
- /**
- * Inject error to test LQHKEYREF handling:
- * Tampering with tableSchemaVersion such that LQH will
- * return LQHKEYREF('1227: Invalid schema version')
- * May happen for different treeNodes in the request:
- * - 17030: Fail on any lookup_send()
- * - 17031: Fail on lookup_send() if 'isLeaf'
- * - 17032: Fail on lookup_send() if treeNode not root
- */
- if (ERROR_INSERTED_CLEAR(17030) ||
- (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17031)) ||
- (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17032)))
- {
- jam();
- req->tableSchemaVersion += (1 << 16); // Provoke 'Invalid schema version'
- }
+ /**
+ * Test execution terminated due to 'NodeFailure' which
+ * may happen for different treeNodes in the request:
+ * - 17020: Fail on any lookup_send()
+ * - 17021: Fail on lookup_send() if 'isLeaf'
+ * - 17022: Fail on lookup_send() if treeNode not root
+ */
+ if (ERROR_INSERTED_CLEAR(17020) ||
+ (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17021)) ||
+ (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17022)))
+ {
+ jam();
+ releaseSections(handle);
+ err = DbspjErr::NodeFailure;
+ break;
+ }
+ if (unlikely(!c_alive_nodes.get(Tnode)))
+ {
+ jam();
+ releaseSections(handle);
+ err = DbspjErr::NodeFailure;
+ break;
+ }
+ else if (! (treeNodePtr.p->isLeaf() && requestPtr.p->isLookup()))
+ {
+ jam();
+ ndbassert(Tnode < NDB_ARRAY_SIZE(requestPtr.p->m_lookup_node_data));
+ requestPtr.p->m_outstanding += cnt;
+ requestPtr.p->m_lookup_node_data[Tnode] += cnt;
+ // number wrapped
+ ndbrequire(! (requestPtr.p->m_lookup_node_data[Tnode] == 0));
+ }
-#if defined DEBUG_LQHKEYREQ
- ndbout_c("LQHKEYREQ to %x", ref);
- printLQHKEYREQ(stdout, signal->getDataPtrSend(),
- NDB_ARRAY_SIZE(treeNodePtr.p->m_lookup_data.m_lqhKeyReq),
- DBLQH);
- printf("KEYINFO: ");
- print(handle.m_ptr[0], stdout);
- printf("ATTRINFO: ");
- print(handle.m_ptr[1], stdout);
-#endif
+ sendSignal(ref, GSN_LQHKEYREQ, signal,
+ NDB_ARRAY_SIZE(treeNodePtr.p->m_lookup_data.m_lqhKeyReq),
+ JBB, &handle);
- Uint32 Tnode = refToNode(ref);
- if (Tnode == getOwnNodeId())
- {
- c_Counters.incr_counter(CI_LOCAL_READS_SENT, 1);
- }
- else
- {
- c_Counters.incr_counter(CI_REMOTE_READS_SENT, 1);
- }
+ treeNodePtr.p->m_lookup_data.m_outstanding += cnt;
+ if (requestPtr.p->isLookup() && treeNodePtr.p->isLeaf())
+ {
+ jam();
+ /**
+ * Send TCKEYCONF with DirtyReadBit + Tnode,
+ * so that API can discover if Tnode while waiting for result
+ */
+ Uint32 resultRef = req->variableData[0];
+ Uint32 resultData = req->variableData[1];
- /**
- * Test execution terminated due to 'NodeFailure' which
- * may happen for different treeNodes in the request:
- * - 17020: Fail on any lookup_send()
- * - 17021: Fail on lookup_send() if 'isLeaf'
- * - 17022: Fail on lookup_send() if treeNode not root
- */
- if (ERROR_INSERTED_CLEAR(17020) ||
- (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17021)) ||
- (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17022)))
- {
- jam();
- releaseSections(handle);
- abort(signal, requestPtr, DbspjErr::NodeFailure);
- return;
- }
- if (unlikely(!c_alive_nodes.get(Tnode)))
- {
- jam();
- releaseSections(handle);
- abort(signal, requestPtr, DbspjErr::NodeFailure);
+ TcKeyConf* conf = (TcKeyConf*)signal->getDataPtrSend();
+ conf->apiConnectPtr = RNIL; // lookup transaction from operations...
+ conf->confInfo = 0;
+ TcKeyConf::setNoOfOperations(conf->confInfo, 1);
+ conf->transId1 = requestPtr.p->m_transId[0];
+ conf->transId2 = requestPtr.p->m_transId[1];
+ conf->operations[0].apiOperationPtr = resultData;
+ conf->operations[0].attrInfoLen = TcKeyConf::DirtyReadBit | Tnode;
+ Uint32 sigLen = TcKeyConf::StaticLength + TcKeyConf::OperationLength;
+ sendTCKEYCONF(signal, sigLen, resultRef, requestPtr.p->m_senderRef);
+ }
return;
}
- else if (! (treeNodePtr.p->isLeaf() && requestPtr.p->isLookup()))
- {
- jam();
- ndbassert(Tnode < NDB_ARRAY_SIZE(requestPtr.p->m_lookup_node_data));
- requestPtr.p->m_outstanding += cnt;
- requestPtr.p->m_lookup_node_data[Tnode] += cnt;
- // number wrapped
- ndbrequire(! (requestPtr.p->m_lookup_node_data[Tnode] == 0));
- }
-
- sendSignal(ref, GSN_LQHKEYREQ, signal,
- NDB_ARRAY_SIZE(treeNodePtr.p->m_lookup_data.m_lqhKeyReq),
- JBB, &handle);
-
- treeNodePtr.p->m_lookup_data.m_outstanding += cnt;
- if (requestPtr.p->isLookup() && treeNodePtr.p->isLeaf())
- {
- jam();
- /**
- * Send TCKEYCONF with DirtyReadBit + Tnode,
- * so that API can discover if Tnode while waiting for result
- */
- Uint32 resultRef = req->variableData[0];
- Uint32 resultData = req->variableData[1];
-
- TcKeyConf* conf = (TcKeyConf*)signal->getDataPtrSend();
- conf->apiConnectPtr = RNIL; // lookup transaction from operations...
- conf->confInfo = 0;
- TcKeyConf::setNoOfOperations(conf->confInfo, 1);
- conf->transId1 = requestPtr.p->m_transId[0];
- conf->transId2 = requestPtr.p->m_transId[1];
- conf->operations[0].apiOperationPtr = resultData;
- conf->operations[0].attrInfoLen = TcKeyConf::DirtyReadBit | Tnode;
- Uint32 sigLen = TcKeyConf::StaticLength + TcKeyConf::OperationLength;
- sendTCKEYCONF(signal, sigLen, resultRef, requestPtr.p->m_senderRef);
- }
+ while (0);
+error:
+ ndbrequire(err);
+ jam();
+ abort(signal, requestPtr, err);
}
void
@@ -3540,7 +3587,32 @@ Dbspj::lookup_parent_row(Signal* signal,
{
jam();
Uint32 tmp = RNIL;
- ndbrequire(dupSection(tmp, attrInfoPtrI)); // TODO handle error
+
+ /**
+ * Test execution terminated due to 'OutOfSectionMemory' which
+ * may happen for different treeNodes in the request:
+ * - 17080: Fail on lookup_parent_row
+ * - 17081: Fail on lookup_parent_row: if 'isLeaf'
+ * - 17082: Fail on lookup_parent_row: if treeNode not root
+ */
+
+ if (ERROR_INSERTED_CLEAR(17080) ||
+ (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17081)) ||
+ (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17082)))
+ {
+ jam();
+ ndbout_c("Injecting OutOfSectionMemory error at line %d file %s",
+ __LINE__, __FILE__);
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ if (!dupSection(tmp, attrInfoPtrI))
+ {
+ jam();
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
Uint32 org_size;
{
@@ -5472,146 +5544,182 @@ Dbspj::scanIndex_send(Signal* signal,
req->batch_size_bytes = bs_bytes;
req->batch_size_rows = bs_rows;
+ Uint32 err = 0;
Uint32 requestsSent = 0;
- Local_ScanFragHandle_list list(m_scanfraghandle_pool, data.m_fragments);
- Ptr<ScanFragHandle> fragPtr;
- list.first(fragPtr);
- Uint32 keyInfoPtrI = fragPtr.p->m_rangePtrI;
- ndbrequire(prune || keyInfoPtrI != RNIL);
- /**
- * Iterate over the list of fragments until we have sent as many
- * SCAN_FRAGREQs as we should.
- */
- while (requestsSent < noOfFrags)
{
- jam();
- ndbassert(!fragPtr.isNull());
-
- if (fragPtr.p->m_state != ScanFragHandle::SFH_NOT_STARTED)
- {
- // Skip forward to the frags that we should send.
- jam();
- list.next(fragPtr);
- continue;
- }
-
- const Uint32 ref = fragPtr.p->m_ref;
-
- if (noOfFrags==1 && !prune &&
- data.m_frags_not_started == data.m_fragCount &&
- refToNode(ref) != getOwnNodeId() &&
- list.hasNext(fragPtr))
+ Local_ScanFragHandle_list list(m_scanfraghandle_pool, data.m_fragments);
+ Ptr<ScanFragHandle> fragPtr;
+ list.first(fragPtr);
+ Uint32 keyInfoPtrI = fragPtr.p->m_rangePtrI;
+ ndbrequire(prune || keyInfoPtrI != RNIL);
+ /**
+ * Iterate over the list of fragments until we have sent as many
+ * SCAN_FRAGREQs as we should.
+ */
+ while (requestsSent < noOfFrags)
{
- /**
- * If we are doing a scan with adaptive parallelism and start with
- * parallelism=1 then it makes sense to fetch a batch from a fragment on
- * the local data node. The reason for this is that if that fragment
- * contains few rows, we may be able to read from several fragments in
- * parallel. Then we minimize the total number of round trips (to remote
- * data nodes) if we fetch the first fragment batch locally.
- */
jam();
- list.next(fragPtr);
- continue;
- }
+ ndbassert(!fragPtr.isNull());
- SectionHandle handle(this);
+ if (fragPtr.p->m_state != ScanFragHandle::SFH_NOT_STARTED)
+ {
+ // Skip forward to the frags that we should send.
+ jam();
+ list.next(fragPtr);
+ continue;
+ }
- Uint32 attrInfoPtrI = treeNodePtr.p->m_send.m_attrInfoPtrI;
+ const Uint32 ref = fragPtr.p->m_ref;
- /**
- * Set data specific for this fragment
- */
- req->senderData = fragPtr.i;
- req->fragmentNoKeyLen = fragPtr.p->m_fragId;
-
- if (prune)
- {
- jam();
- keyInfoPtrI = fragPtr.p->m_rangePtrI;
- if (keyInfoPtrI == RNIL)
+ if (noOfFrags==1 && !prune &&
+ data.m_frags_not_started == data.m_fragCount &&
+ refToNode(ref) != getOwnNodeId() &&
+ list.hasNext(fragPtr))
{
/**
- * Since we use pruning, we can see that no parent rows would hash
- * to this fragment.
+ * If we are doing a scan with adaptive parallelism and start with
+ * parallelism=1 then it makes sense to fetch a batch from a fragment on
+ * the local data node. The reason for this is that if that fragment
+ * contains few rows, we may be able to read from several fragments in
+ * parallel. Then we minimize the total number of round trips (to remote
+ * data nodes) if we fetch the first fragment batch locally.
*/
jam();
- fragPtr.p->m_state = ScanFragHandle::SFH_COMPLETE;
list.next(fragPtr);
continue;
}
- if (!repeatable)
+ SectionHandle handle(this);
+
+ Uint32 attrInfoPtrI = treeNodePtr.p->m_send.m_attrInfoPtrI;
+
+ /**
+ * Set data specific for this fragment
+ */
+ req->senderData = fragPtr.i;
+ req->fragmentNoKeyLen = fragPtr.p->m_fragId;
+
+ if (prune)
{
- /**
- * If we'll use sendSignal() and we need to send the attrInfo several
- * times, we need to copy them. (For repeatable or unpruned scans
- * we use sendSignalNoRelease(), so then we do not need to copy.)
- */
jam();
- Uint32 tmp = RNIL;
- ndbrequire(dupSection(tmp, attrInfoPtrI)); // TODO handle error
- attrInfoPtrI = tmp;
+ keyInfoPtrI = fragPtr.p->m_rangePtrI;
+ if (keyInfoPtrI == RNIL)
+ {
+ /**
+ * Since we use pruning, we can see that no parent rows would hash
+ * to this fragment.
+ */
+ jam();
+ fragPtr.p->m_state = ScanFragHandle::SFH_COMPLETE;
+ list.next(fragPtr);
+ continue;
+ }
+
+ if (!repeatable)
+ {
+ /**
+ * If we'll use sendSignal() and we need to send the attrInfo several
+ * times, we need to copy them. (For repeatable or unpruned scans
+ * we use sendSignalNoRelease(), so then we do not need to copy.)
+ */
+ jam();
+ Uint32 tmp = RNIL;
+
+ /**
+ * Test execution terminated due to 'OutOfSectionMemory' which
+ * may happen for different treeNodes in the request:
+ * - 17090: Fail on any scanIndex_send()
+ * - 17091: Fail after sending SCAN_FRAGREQ to some fragments
+ * - 17092: Fail on scanIndex_send() if 'isLeaf'
+ * - 17093: Fail on scanIndex_send() if treeNode not root
+ */
+
+ if (ERROR_INSERTED_CLEAR(17090) ||
+ (requestsSent > 1 && ERROR_INSERTED_CLEAR(17091)) ||
+ (treeNodePtr.p->isLeaf() && ERROR_INSERTED_CLEAR(17092)) ||
+ (treeNodePtr.p->m_parentPtrI != RNIL && ERROR_INSERTED_CLEAR(17093)))
+ {
+ jam();
+ ndbout_c("Injecting OutOfSectionMemory error at line %d file %s",
+ __LINE__, __FILE__);
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ if (!dupSection(tmp, attrInfoPtrI))
+ {
+ jam();
+ err = DbspjErr::OutOfSectionMemory;
+ break;
+ }
+
+ attrInfoPtrI = tmp;
+ }
}
- }
- req->variableData[0] = batchRange;
- getSection(handle.m_ptr[0], attrInfoPtrI);
- getSection(handle.m_ptr[1], keyInfoPtrI);
- handle.m_cnt = 2;
+ req->variableData[0] = batchRange;
+ getSection(handle.m_ptr[0], attrInfoPtrI);
+ getSection(handle.m_ptr[1], keyInfoPtrI);
+ handle.m_cnt = 2;
#if defined DEBUG_SCAN_FRAGREQ
- ndbout_c("SCAN_FRAGREQ to %x", ref);
- printSCAN_FRAGREQ(stdout, signal->getDataPtrSend(),
- NDB_ARRAY_SIZE(treeNodePtr.p->m_scanfrag_data.m_scanFragReq),
- DBLQH);
- printf("ATTRINFO: ");
- print(handle.m_ptr[0], stdout);
- printf("KEYINFO: ");
- print(handle.m_ptr[1], stdout);
+ ndbout_c("SCAN_FRAGREQ to %x", ref);
+ printSCAN_FRAGREQ(stdout, signal->getDataPtrSend(),
+ NDB_ARRAY_SIZE(treeNodePtr.p->m_scanfrag_data.m_scanFragReq),
+ DBLQH);
+ printf("ATTRINFO: ");
+ print(handle.m_ptr[0], stdout);
+ printf("KEYINFO: ");
+ print(handle.m_ptr[1], stdout);
#endif
- if (refToNode(ref) == getOwnNodeId())
- {
- c_Counters.incr_counter(CI_LOCAL_RANGE_SCANS_SENT, 1);
- }
- else
- {
- c_Counters.incr_counter(CI_REMOTE_RANGE_SCANS_SENT, 1);
- }
+ if (refToNode(ref) == getOwnNodeId())
+ {
+ c_Counters.incr_counter(CI_LOCAL_RANGE_SCANS_SENT, 1);
+ }
+ else
+ {
+ c_Counters.incr_counter(CI_REMOTE_RANGE_SCANS_SENT, 1);
+ }
- if (prune && !repeatable)
- {
- /**
- * For a non-repeatable pruned scan, key info is unique for each
- * fragment and therefore cannot be reused, so we release key info
- * right away.
- */
- jam();
- sendSignal(ref, GSN_SCAN_FRAGREQ, signal,
- NDB_ARRAY_SIZE(data.m_scanFragReq), JBB, &handle);
- fragPtr.p->m_rangePtrI = RNIL;
- fragPtr.p->reset_ranges();
- }
- else
- {
- /**
- * Reuse key info for multiple fragments and/or multiple repetitions
- * of the scan.
- */
- jam();
- sendSignalNoRelease(ref, GSN_SCAN_FRAGREQ, signal,
- NDB_ARRAY_SIZE(data.m_scanFragReq), JBB, &handle);
- }
- handle.clear();
+ if (prune && !repeatable)
+ {
+ /**
+ * For a non-repeatable pruned scan, key info is unique for each
+ * fragment and therefore cannot be reused, so we release key info
+ * right away.
+ */
+ jam();
+ sendSignal(ref, GSN_SCAN_FRAGREQ, signal,
+ NDB_ARRAY_SIZE(data.m_scanFragReq), JBB, &handle);
+ fragPtr.p->m_rangePtrI = RNIL;
+ fragPtr.p->reset_ranges();
+ }
+ else
+ {
+ /**
+ * Reuse key info for multiple fragments and/or multiple repetitions
+ * of the scan.
+ */
+ jam();
+ sendSignalNoRelease(ref, GSN_SCAN_FRAGREQ, signal,
+ NDB_ARRAY_SIZE(data.m_scanFragReq), JBB, &handle);
+ }
+ handle.clear();
- fragPtr.p->m_state = ScanFragHandle::SFH_SCANNING; // running
- data.m_frags_outstanding++;
- data.m_frags_not_started--;
- batchRange += bs_rows;
- requestsSent++;
- list.next(fragPtr);
- } // while (requestsSent < noOfFrags)
+ fragPtr.p->m_state = ScanFragHandle::SFH_SCANNING; // running
+ data.m_frags_outstanding++;
+ data.m_frags_not_started--;
+ batchRange += bs_rows;
+ requestsSent++;
+ list.next(fragPtr);
+ } // while (requestsSent < noOfFrags)
+ }
+ if (err)
+ {
+ jam();
+ abort(signal, requestPtr, err);
+ }
return requestsSent;
}
@@ -6838,10 +6946,6 @@ Dbspj::appendFromParent(Uint32 & dst, Lo
// should have been expanded during build
DEBUG_CRASH();
return DbspjErr::InvalidPattern;
- default:
- jam();
- DEBUG_CRASH();
- return DbspjErr::InvalidPattern;
}
}
=== modified file 'storage/ndb/test/ndbapi/testSpj.cpp'
--- a/storage/ndb/test/ndbapi/testSpj.cpp 2012-03-01 15:13:54 +0000
+++ b/storage/ndb/test/ndbapi/testSpj.cpp 2012-03-15 14:33:38 +0000
@@ -31,7 +31,7 @@ static int faultToInject = 0;
enum faultsToInject {
FI_START = 17001,
- FI_END = 17063
+ FI_END = 17093
};
int
@@ -120,7 +120,9 @@ runLookupJoinError(NDBT_Context* ctx, ND
17030, 17031, 17032, // LQHKEYREQ reply is LQHKEYREF('Invalid..')
17040, 17041, 17042, // lookup_parent_row -> OutOfQueryMemory
17050, 17051, 17052, 17053, // parseDA -> outOfSectionMem
- 17060, 17061, 17062, 17063 // scanIndex_parent_row -> outOfSectionMem
+ 17060, 17061, 17062, 17063, // scanIndex_parent_row -> outOfSectionMem
+ 17070, 17071, 17072, // lookup_send.dupsec -> outOfSectionMem
+ 17080, 17081, 17082 // lookup_parent_row -> OutOfQueryMemory
};
loops = faultToInject ? 1 : sizeof(lookupFaults)/sizeof(int);
@@ -206,7 +208,10 @@ runScanJoinError(NDBT_Context* ctx, NDBT
17030, 17031, 17032, // LQHKEYREQ reply is LQHKEYREF('Invalid..')
17040, 17041, 17042, // lookup_parent_row -> OutOfQueryMemory
17050, 17051, 17052, 17053, // parseDA -> outOfSectionMem
- 17060, 17061, 17062, 17063 // scanIndex_parent_row -> outOfSectionMem
+ 17060, 17061, 17062, 17063, // scanIndex_parent_row -> outOfSectionMem
+ 17070, 17071, 17072, // lookup_send.dupsec -> outOfSectionMem
+ 17080, 17081, 17082, // lookup_parent_row -> OutOfQueryMemory
+ 17090, 17091, 17092, 17093 // scanIndex_send -> OutOfQueryMemory
};
loops = faultToInject ? 1 : sizeof(scanFaults)/sizeof(int);
No bundle (reason: useless for push emails).
| Thread |
|---|
| • bzr push into mysql-5.1-telco-7.0-spj-scan-vs-scan branch(maitrayi.sabaratnam:3599 to 3600) | Maitrayi Sabaratnam | 15 Mar |