testTimeout.cpp
上传用户:romrleung
上传日期:2022-05-23
资源大小:18897k
文件大小:13k
源码类别:

MySQL数据库

开发平台:

Visual C++

  1. /* Copyright (C) 2003 MySQL AB
  2.    This program is free software; you can redistribute it and/or modify
  3.    it under the terms of the GNU General Public License as published by
  4.    the Free Software Foundation; either version 2 of the License, or
  5.    (at your option) any later version.
  6.    This program is distributed in the hope that it will be useful,
  7.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  8.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  9.    GNU General Public License for more details.
  10.    You should have received a copy of the GNU General Public License
  11.    along with this program; if not, write to the Free Software
  12.    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
  13. #include <NDBT.hpp>
  14. #include <NDBT_Test.hpp>
  15. #include <HugoTransactions.hpp>
  16. #include <UtilTransactions.hpp>
  17. #include <random.h>
  18. #include <NdbConfig.hpp>
  19. #include <signaldata/DumpStateOrd.hpp>
  20. #define TIMEOUT (Uint32)3000
  21. Uint32 g_org_timeout = 3000;
  22. int
  23. setTransactionTimeout(NDBT_Context* ctx, NDBT_Step* step){
  24.   NdbRestarter restarter;
  25.   int timeout = ctx->getProperty("TransactionInactiveTimeout",TIMEOUT);
  26.   NdbConfig conf(GETNDB(step)->getNodeId()+1);
  27.   unsigned int nodeId = conf.getMasterNodeId();
  28.   if (!conf.getProperty(nodeId,
  29. NODE_TYPE_DB, 
  30. CFG_DB_TRANSACTION_INACTIVE_TIMEOUT,
  31. &g_org_timeout)){
  32.     return NDBT_FAILED;
  33.   }
  34.   int val[] = { DumpStateOrd::TcSetApplTransactionTimeout, timeout };
  35.   if(restarter.dumpStateAllNodes(val, 2) != 0){
  36.     return NDBT_FAILED;
  37.   }
  38.   
  39.   return NDBT_OK;
  40. }
  41. int
  42. resetTransactionTimeout(NDBT_Context* ctx, NDBT_Step* step){
  43.   NdbRestarter restarter;
  44.   
  45.   int val[] = { DumpStateOrd::TcSetApplTransactionTimeout, g_org_timeout };
  46.   if(restarter.dumpStateAllNodes(val, 2) != 0){
  47.     return NDBT_FAILED;
  48.   }
  49.   
  50.   return NDBT_OK;
  51. }
  52. int runLoadTable(NDBT_Context* ctx, NDBT_Step* step){
  53.   int records = ctx->getNumRecords();
  54.   HugoTransactions hugoTrans(*ctx->getTab());
  55.   if (hugoTrans.loadTable(GETNDB(step), records) != 0){
  56.     return NDBT_FAILED;
  57.   }
  58.   return NDBT_OK;
  59. }
  60. int runClearTable(NDBT_Context* ctx, NDBT_Step* step){
  61.   int records = ctx->getNumRecords();
  62.   
  63.   UtilTransactions utilTrans(*ctx->getTab());
  64.   if (utilTrans.clearTable2(GETNDB(step),  records) != 0){
  65.     return NDBT_FAILED;
  66.   }
  67.   return NDBT_OK;
  68. }
  69. #define CHECK(b) if (!(b)) { 
  70.   ndbout << "ERR: "<< step->getName() 
  71.          << " failed on line " << __LINE__ << endl; 
  72.   result = NDBT_FAILED; 
  73.   break; }
  74. int runTimeoutTrans(NDBT_Context* ctx, NDBT_Step* step){
  75.   int result = NDBT_OK;
  76.   int loops = ctx->getNumLoops();
  77.   NdbConfig conf(GETNDB(step)->getNodeId()+1);
  78.   unsigned int nodeId = conf.getMasterNodeId();
  79.   int stepNo = step->getStepNo();
  80.   int timeout = ctx->getProperty("TransactionInactiveTimeout",TIMEOUT);
  81.   int minSleep = (int)(timeout * 1.5);
  82.   int maxSleep = timeout * 2;
  83.   ndbout << "TransactionInactiveTimeout="<< timeout
  84.  << ", minSleep="<<minSleep
  85.  << ", maxSleep="<<maxSleep<<endl;
  86.   HugoOperations hugoOps(*ctx->getTab());
  87.   Ndb* pNdb = GETNDB(step);
  88.   for (int l = 0; l < loops && result == NDBT_OK; l++){
  89.     do{
  90.       // Commit transaction
  91.       CHECK(hugoOps.startTransaction(pNdb) == 0);
  92.       CHECK(hugoOps.pkReadRecord(pNdb, stepNo) == 0);
  93.       CHECK(hugoOps.execute_NoCommit(pNdb) == 0);
  94.       
  95.       int sleep = minSleep + myRandom48(maxSleep-minSleep);   
  96.       ndbout << "Sleeping for " << sleep << " milliseconds" << endl;
  97.       NdbSleep_MilliSleep(sleep);
  98.       
  99.       // Expect that transaction has timed-out
  100.       CHECK(hugoOps.execute_Commit(pNdb) == 237); 
  101.     } while(false);
  102.     hugoOps.closeTransaction(pNdb);
  103.   }
  104.   return result;
  105. }
  106. int runTimeoutTrans2(NDBT_Context* ctx, NDBT_Step* step){
  107.   int result = NDBT_OK;
  108.   int loops = ctx->getNumLoops();
  109.   int stepNo = step->getStepNo();
  110.   int mul1 = ctx->getProperty("Op1", (Uint32)0);
  111.   int mul2 = ctx->getProperty("Op2", (Uint32)0);
  112.   int records = ctx->getNumRecords();
  113.   int timeout = ctx->getProperty("TransactionInactiveTimeout",TIMEOUT);
  114.   int minSleep = (int)(timeout * 1.5);
  115.   int maxSleep = timeout * 2;
  116.   
  117.   HugoOperations hugoOps(*ctx->getTab());
  118.   Ndb* pNdb = GETNDB(step);
  119.   for (int l = 0; l<loops && !ctx->isTestStopped() && result == NDBT_OK; l++){
  120.     
  121.     int op1 = 0 + (l + stepNo) * mul1;
  122.     int op2 = 0 + (l + stepNo) * mul2;
  123.     op1 = (op1 % 5);
  124.     op2 = (op2 % 5);
  125.     ndbout << stepNo << ": TransactionInactiveTimeout="<< timeout
  126.    << ", minSleep="<<minSleep
  127.    << ", maxSleep="<<maxSleep
  128.    << ", op1=" << op1
  129.    << ", op2=" << op2 << endl;;
  130.     
  131.     do{
  132.       // Commit transaction
  133.       CHECK(hugoOps.startTransaction(pNdb) == 0);
  134.       
  135.       switch(op1){
  136.       case 0:
  137. break;
  138.       case 1:
  139. if(hugoOps.pkReadRecord(pNdb, stepNo) != 0){
  140.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  141.   result = NDBT_FAILED; break;
  142. }
  143. break;
  144.       case 2:
  145. if(hugoOps.pkUpdateRecord(pNdb, stepNo) != 0){
  146.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  147.   result = NDBT_FAILED; break;
  148. }
  149. break;
  150.       case 3:
  151. if(hugoOps.pkDeleteRecord(pNdb, stepNo) != 0){
  152.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  153.   result = NDBT_FAILED; break;
  154. }
  155. break;
  156.       case 4:
  157. if(hugoOps.pkInsertRecord(pNdb, stepNo+records+l) != 0){
  158.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  159.   result = NDBT_FAILED; break;
  160. }
  161. break;
  162.       }
  163.       
  164.       if(result != NDBT_OK)
  165. break;
  166.       int res = hugoOps.execute_NoCommit(pNdb);
  167.       if(res != 0){
  168. g_err << stepNo << ": Fail" << __LINE__ << endl;
  169. result = NDBT_FAILED; break;
  170.       }
  171.       
  172.       int sleep = minSleep + myRandom48(maxSleep-minSleep);   
  173.       ndbout << stepNo << ": Sleeping for "<< sleep << " milliseconds" << endl;
  174.       NdbSleep_MilliSleep(sleep);
  175.       
  176.       switch(op2){
  177.       case 0:
  178. break;
  179.       case 1:
  180. if(hugoOps.pkReadRecord(pNdb, stepNo) != 0){
  181.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  182.   result = NDBT_FAILED; break;
  183. }
  184. break;
  185.       case 2:
  186. if(hugoOps.pkUpdateRecord(pNdb, stepNo) != 0){
  187.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  188.   result = NDBT_FAILED; break;
  189. }
  190. break;
  191.       case 3:
  192. if(hugoOps.pkDeleteRecord(pNdb, stepNo) != 0){
  193.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  194.   result = NDBT_FAILED; break;
  195. }
  196. break;
  197.       case 4:
  198. if(hugoOps.pkInsertRecord(pNdb, stepNo+2*records+l) != 0){
  199.   g_err << stepNo << ": Fail" << __LINE__ << endl;
  200.   result = NDBT_FAILED; break;
  201. }
  202. break;
  203.       }
  204.       // Expect that transaction has timed-out
  205.       res = hugoOps.execute_Commit(pNdb);
  206.       if(op1 != 0 && res != 266){
  207. g_err << stepNo << ": Fail: " << res << "!= 237, op1=" 
  208.       << op1 << ", op2=" << op2 << endl;
  209. result = NDBT_FAILED; break;
  210.       }
  211.       
  212.     } while(false);
  213.     
  214.     hugoOps.closeTransaction(pNdb);
  215.   }
  216.   return result;
  217. }
  218. int runDontTimeoutTrans(NDBT_Context* ctx, NDBT_Step* step){
  219.   int result = NDBT_OK;
  220.   int loops = ctx->getNumLoops();
  221.   int stepNo = step->getStepNo();
  222.   int timeout = ctx->getProperty("TransactionInactiveTimeout",TIMEOUT);
  223.   int maxSleep = (int)(timeout * 0.5);
  224.   ndbout << "TransactionInactiveTimeout="<< timeout
  225.  << ", maxSleep="<<maxSleep<<endl;
  226.   HugoOperations hugoOps(*ctx->getTab());
  227.   Ndb* pNdb = GETNDB(step);
  228.   for (int l = 0; l < loops && result == NDBT_OK; l++){
  229.     do{
  230.       // Commit transaction
  231.       CHECK(hugoOps.startTransaction(pNdb) == 0);
  232.       CHECK(hugoOps.pkReadRecord(pNdb, stepNo) == 0);
  233.       CHECK(hugoOps.execute_NoCommit(pNdb) == 0);
  234.       
  235.       int sleep = myRandom48(maxSleep);   
  236.       ndbout << "Sleeping for " << sleep << " milliseconds" << endl;
  237.       NdbSleep_MilliSleep(sleep);
  238.       
  239.       // Expect that transaction has NOT timed-out
  240.       CHECK(hugoOps.execute_Commit(pNdb) == 0); 
  241.     
  242.     } while(false);
  243.     hugoOps.closeTransaction(pNdb);
  244.   }
  245.     
  246.   return result;
  247. }
  248. int runDeadlockTimeoutTrans(NDBT_Context* ctx, NDBT_Step* step){
  249.   int result = NDBT_OK;
  250.   int loops = ctx->getNumLoops();
  251.   int stepNo = step->getStepNo();
  252.   Uint32 deadlock_timeout;
  253.   NdbConfig conf(GETNDB(step)->getNodeId()+1);
  254.   unsigned int nodeId = conf.getMasterNodeId();
  255.   if (!conf.getProperty(nodeId,
  256.                         NODE_TYPE_DB,
  257.                         CFG_DB_TRANSACTION_DEADLOCK_TIMEOUT,
  258.                         &deadlock_timeout)){
  259.     return NDBT_FAILED;
  260.   }
  261.   int do_sleep = (int)(deadlock_timeout * 0.5);
  262.   HugoOperations hugoOps(*ctx->getTab());
  263.   Ndb* pNdb = GETNDB(step);
  264.   for (int l = 0; l < loops && result == NDBT_OK; l++){
  265.     do{
  266.       // Commit transaction
  267.       CHECK(hugoOps.startTransaction(pNdb) == 0);
  268.       CHECK(hugoOps.pkReadRecord(pNdb, stepNo) == 0);
  269.       CHECK(hugoOps.execute_NoCommit(pNdb) == 0);
  270.       int sleep = deadlock_timeout * 1.5 + myRandom48(do_sleep);
  271.       ndbout << "Sleeping for " << sleep << " milliseconds" << endl;
  272.       NdbSleep_MilliSleep(sleep);
  273.       // Expect that transaction has NOT timed-out
  274.       CHECK(hugoOps.execute_Commit(pNdb) == 0);
  275.     } while(false);
  276.     hugoOps.closeTransaction(pNdb);
  277.   }
  278.   return result;
  279. }
  280. int runBuddyTransNoTimeout(NDBT_Context* ctx, NDBT_Step* step){
  281.   int result = NDBT_OK;
  282.   int loops = ctx->getNumLoops();
  283.   int records = ctx->getNumRecords();
  284.   int stepNo = step->getStepNo();
  285.   int maxSleep = (int)(TIMEOUT * 0.3);
  286.   ndbout << "TransactionInactiveTimeout="<< TIMEOUT
  287.  << ", maxSleep="<<maxSleep<<endl;
  288.   HugoOperations hugoOps(*ctx->getTab());
  289.   Ndb* pNdb = GETNDB(step);
  290.   for (int l = 1; l < loops && result == NDBT_OK; l++){
  291.     do{
  292.       // Start an insert trans
  293.       CHECK(hugoOps.startTransaction(pNdb) == 0);
  294.       int recordNo = records + (stepNo*loops) + l;
  295.       CHECK(hugoOps.pkInsertRecord(pNdb, recordNo) == 0);
  296.       CHECK(hugoOps.execute_NoCommit(pNdb) == 0);
  297.       
  298.       for (int i = 0; i < 3; i++){
  299. // Perform buddy scan reads
  300. CHECK((hugoOps.scanReadRecords(pNdb)) == 0);
  301. CHECK(hugoOps.execute_NoCommit(pNdb) == 0); 
  302. int sleep = myRandom48(maxSleep);   
  303. ndbout << "Sleeping for " << sleep << " milliseconds" << endl;
  304. NdbSleep_MilliSleep(sleep);
  305.       }
  306.       // Expect that transaction has NOT timed-out
  307.       CHECK(hugoOps.execute_Commit(pNdb) == 0); 
  308.     
  309.     } while(false);
  310.     hugoOps.closeTransaction(pNdb);
  311.   }
  312.   return result;
  313. }
  314. NDBT_TESTSUITE(testTimeout);
  315. TESTCASE("DontTimeoutTransaction", 
  316.  "Test that the transaction does not timeout "
  317.  "if we sleep during the transaction. Use a sleep "
  318.  "value which is smaller than TransactionInactiveTimeout"){
  319.   INITIALIZER(runLoadTable);
  320.   INITIALIZER(setTransactionTimeout);
  321.   STEPS(runDontTimeoutTrans, 1); 
  322.   FINALIZER(resetTransactionTimeout);
  323.   FINALIZER(runClearTable);
  324. }
  325. TESTCASE("Bug11290",
  326.          "Setting TransactionInactiveTimeout to 0(zero) "
  327.          "should result in infinite timeout, and not as "
  328.          "was the bug, a timeout that is equal to the deadlock timeout"){
  329.   TC_PROPERTY("TransactionInactiveTimeout",(Uint32)0);
  330.   INITIALIZER(runLoadTable);
  331.   INITIALIZER(setTransactionTimeout);
  332.   STEPS(runDeadlockTimeoutTrans, 1);
  333.   FINALIZER(resetTransactionTimeout);
  334.   FINALIZER(runClearTable);
  335. }
  336. TESTCASE("DontTimeoutTransaction5", 
  337.  "Test that the transaction does not timeout "
  338.  "if we sleep during the transaction. Use a sleep "
  339.  "value which is smaller than TransactionInactiveTimeout" 
  340.  "Five simultaneous threads"){
  341.   INITIALIZER(runLoadTable);
  342.   INITIALIZER(setTransactionTimeout);
  343.   STEPS(runDontTimeoutTrans, 5); 
  344.   FINALIZER(resetTransactionTimeout);
  345.   FINALIZER(runClearTable);
  346. }
  347. TESTCASE("TimeoutTransaction", 
  348.  "Test that the transaction does timeout "
  349.  "if we sleep during the transaction. Use a sleep "
  350.  "value which is larger than TransactionInactiveTimeout"){
  351.   INITIALIZER(runLoadTable);
  352.   INITIALIZER(setTransactionTimeout);
  353.   STEPS(runTimeoutTrans, 1);
  354.   FINALIZER(resetTransactionTimeout);
  355.   FINALIZER(runClearTable);
  356. }
  357. TESTCASE("TimeoutTransaction5", 
  358.  "Test that the transaction does timeout " 
  359.  "if we sleep during the transaction. Use a sleep " 
  360.  "value which is larger than TransactionInactiveTimeout" 
  361.  "Five simultaneous threads"){
  362.   INITIALIZER(runLoadTable);
  363.   INITIALIZER(setTransactionTimeout);
  364.   STEPS(runTimeoutTrans, 5);
  365.   FINALIZER(resetTransactionTimeout);
  366.   FINALIZER(runClearTable);
  367. }
  368. TESTCASE("TimeoutRandTransaction", 
  369.  "Test that the transaction does timeout "
  370.  "if we sleep during the transaction. Use a sleep "
  371.  "value which is larger than TransactionInactiveTimeout"){
  372.   INITIALIZER(runLoadTable);
  373.   INITIALIZER(setTransactionTimeout);
  374.   TC_PROPERTY("Op1", 7);
  375.   TC_PROPERTY("Op2", 11);
  376.   STEPS(runTimeoutTrans2, 5);
  377.   FINALIZER(resetTransactionTimeout);
  378.   FINALIZER(runClearTable);
  379. }
  380. TESTCASE("BuddyTransNoTimeout", 
  381.  "Start a transaction and perform an insert with NoCommit. " 
  382.  "Start a buddy transaction wich performs long running scans " 
  383.  "and sleeps. " 
  384.  "The total sleep time is longer than TransactionInactiveTimeout" 
  385.  "Commit the first transaction, it should not have timed out."){
  386.   INITIALIZER(runLoadTable);
  387.   INITIALIZER(setTransactionTimeout);
  388.   STEPS(runBuddyTransNoTimeout, 1);
  389.   FINALIZER(resetTransactionTimeout);
  390.   FINALIZER(runClearTable);
  391. }
  392. TESTCASE("BuddyTransNoTimeout5", 
  393.  "Start a transaction and perform an insert with NoCommit. " 
  394.  "Start a buddy transaction wich performs long running scans " 
  395.  "and sleeps. " 
  396.  "The total sleep time is longer than TransactionInactiveTimeout" 
  397.  "Commit the first transaction, it should not have timed out." 
  398.  "Five simultaneous threads"){
  399.   INITIALIZER(runLoadTable);
  400.   INITIALIZER(setTransactionTimeout);
  401.   STEPS(runBuddyTransNoTimeout, 5);
  402.   FINALIZER(resetTransactionTimeout);
  403.   FINALIZER(runClearTable);
  404. }
  405. NDBT_TESTSUITE_END(testTimeout);
  406. int main(int argc, const char** argv){
  407.   ndb_init();
  408.   myRandom48Init(NdbTick_CurrentMillisecond());
  409.   return testTimeout.execute(argc, argv);
  410. }