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

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. #define DBTUP_C
  14. #include "Dbtup.hpp"
  15. #include <RefConvert.hpp>
  16. #include <ndb_limits.h>
  17. #include <pc.hpp>
  18. #include <signaldata/FsConf.hpp>
  19. #include <signaldata/FsRef.hpp>
  20. #define ljam() { jamLine(10000 + __LINE__); }
  21. #define ljamEntry() { jamEntryLine(10000 + __LINE__); }
  22. /* ---------------------------------------------------------------- */
  23. /* ---------------------------------------------------------------- */
  24. /* -------------------- LOCAL CHECKPOINT MODULE ------------------- */
  25. /* ---------------------------------------------------------------- */
  26. /* ---------------------------------------------------------------- */
  27. void Dbtup::execTUP_PREPLCPREQ(Signal* signal) 
  28. {
  29.   CheckpointInfoPtr ciPtr;
  30.   DiskBufferSegmentInfoPtr dbsiPtr;
  31.   FragrecordPtr regFragPtr;
  32.   LocalLogInfoPtr lliPtr;
  33.   TablerecPtr regTabPtr;
  34.   ljamEntry();
  35.   Uint32 userptr = signal->theData[0];
  36.   BlockReference userblockref = signal->theData[1];
  37.   regTabPtr.i = signal->theData[2];
  38.   ptrCheckGuard(regTabPtr, cnoOfTablerec, tablerec);
  39.   Uint32 fragId = signal->theData[3];
  40.   Uint32 checkpointNumber = signal->theData[4];
  41.   cundoFileVersion = signal->theData[5];
  42.   getFragmentrec(regFragPtr, fragId, regTabPtr.p);
  43.   ndbrequire(regTabPtr.i != RNIL);
  44.   seizeCheckpointInfoRecord(ciPtr);
  45.   lliPtr.i = (cundoFileVersion << 2) + (regTabPtr.i & 0x3);
  46.   ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  47.   cnoOfDataPagesToDiskWithoutSynch = 0;
  48.   ciPtr.p->lcpDataFileHandle = RNIL;
  49.   ciPtr.p->lcpCheckpointVersion = checkpointNumber;
  50.   ciPtr.p->lcpLocalLogInfoP = lliPtr.i;
  51.   ciPtr.p->lcpFragmentP = regFragPtr.i; /* SET THE FRAGMENT              */
  52.   ciPtr.p->lcpFragmentId = fragId; /* SAVE THE FRAGMENT IDENTITY    */
  53.   ciPtr.p->lcpTabPtr = regTabPtr.i; /* SET THE TABLE POINTER         */
  54.   ciPtr.p->lcpBlockref = userblockref; /* SET THE BLOCK REFERENCE       */
  55.   ciPtr.p->lcpUserptr = userptr; /* SET THE USERPOINTER           */
  56.    /***************************************************************/
  57.    /* OPEN THE UNDO FILE FOR WRITE                                */
  58.    /* UPON FSOPENCONF                                             */
  59.    /***************************************************************/
  60.   if (lliPtr.p->lliActiveLcp == 0) {                  /* IS THE UNDO LOG FILE OPEN?    */
  61.     PendingFileOpenInfoPtr undoPfoiPtr;
  62.     UndoPagePtr regUndoPagePtr;
  63.     ljam();
  64.     lliPtr.p->lliPrevRecordId = 0;
  65.     lliPtr.p->lliLogFilePage = 0;
  66.     lliPtr.p->lliUndoPagesToDiskWithoutSynch = 0;
  67.     lliPtr.p->lliUndoWord = ZUNDO_PAGE_HEADER_SIZE;
  68.     seizeUndoBufferSegment(signal, regUndoPagePtr);
  69.     seizeDiskBufferSegmentRecord(dbsiPtr);
  70.     dbsiPtr.p->pdxBuffertype = UNDO_PAGES;
  71.     for (Uint32 i = 0; i < ZUB_SEGMENT_SIZE; i++) {
  72.       dbsiPtr.p->pdxDataPage[i] = regUndoPagePtr.i + i;
  73.     }//for
  74.     dbsiPtr.p->pdxFilePage = lliPtr.p->lliLogFilePage;
  75.     lliPtr.p->lliUndoPage = regUndoPagePtr.i;
  76.     lliPtr.p->lliUndoBufferSegmentP = dbsiPtr.i;
  77.                                                 /* F LEVEL NOT USED              */
  78.     Uint32 fileType = 1;                 /* VERSION                       */
  79.     fileType = (fileType << 8) | 2;         /* .LOCLOG                       */
  80.     fileType = (fileType << 8) | 6;         /* D6                            */
  81.     fileType = (fileType << 8) | 0xff;         /* DON'T USE P DIRECTORY LEVEL   */
  82.     Uint32 fileFlag = 0x301;                 /* CREATE, WRITE ONLY, TRUNCATE  */
  83.     seizePendingFileOpenInfoRecord(undoPfoiPtr);
  84.     undoPfoiPtr.p->pfoOpenType = LCP_UNDO_FILE_WRITE;
  85.     undoPfoiPtr.p->pfoCheckpointInfoP = ciPtr.i;
  86.     signal->theData[0] = cownref;
  87.     signal->theData[1] = undoPfoiPtr.i;
  88.     signal->theData[2] = lliPtr.i;
  89.     signal->theData[3] = 0xFFFFFFFF;
  90.     signal->theData[4] = cundoFileVersion;
  91.     signal->theData[5] = fileType;
  92.     signal->theData[6] = fileFlag;
  93.     sendSignal(NDBFS_REF, GSN_FSOPENREQ, signal, 7, JBA);
  94.   }//if
  95.    /***************************************************************/
  96.    /* OPEN THE DATA FILE FOR WRITE                                */
  97.    /* THE FILE HANDLE WILL BE SET IN THE CHECKPOINT_INFO_RECORD   */
  98.    /* UPON FSOPENCONF                                             */
  99.    /***************************************************************/
  100.    /* OPEN THE DATA FILE IN THE FOLLOWING FORM              */
  101.    /* D5/DBTUP/T<TABID>/F<FRAGID>/S<CHECKPOINT_NUMBER>.DATA */
  102.   PendingFileOpenInfoPtr dataPfoiPtr;
  103.   Uint32 fileType = 1;                 /* VERSION                       */
  104.   fileType = (fileType << 8) | 0; /* .DATA                         */
  105.   fileType = (fileType << 8) | 5; /* D5                            */
  106.   fileType = (fileType << 8) | 0xff; /* DON'T USE P DIRECTORY LEVEL   */
  107.   Uint32 fileFlag = 0x301;         /* CREATE, WRITE ONLY, TRUNCATE  */
  108.   seizePendingFileOpenInfoRecord(dataPfoiPtr); /* SEIZE A NEW FILE OPEN INFO    */
  109.   if (lliPtr.p->lliActiveLcp == 0) {
  110.     ljam();
  111.     dataPfoiPtr.p->pfoOpenType = LCP_DATA_FILE_WRITE_WITH_UNDO;
  112.   } else {
  113.     ljam();
  114.     dataPfoiPtr.p->pfoOpenType = LCP_DATA_FILE_WRITE;
  115.   }//if
  116.   dataPfoiPtr.p->pfoCheckpointInfoP = ciPtr.i;
  117.    /* LET'S OPEN THE DATA FILE FOR WRITE */
  118.    /* INCREASE NUMBER OF ACTIVE CHECKPOINTS */
  119.   lliPtr.p->lliActiveLcp = 1;
  120.   signal->theData[0] = cownref;
  121.   signal->theData[1] = dataPfoiPtr.i;
  122.   signal->theData[2] = ciPtr.p->lcpTabPtr;
  123.   signal->theData[3] = ciPtr.p->lcpFragmentId;
  124.   signal->theData[4] = ciPtr.p->lcpCheckpointVersion;
  125.   signal->theData[5] = fileType;
  126.   signal->theData[6] = fileFlag;
  127.   sendSignal(NDBFS_REF, GSN_FSOPENREQ, signal, 7, JBA);
  128.   return;
  129. }//Dbtup::execTUP_PREPLCPREQ()
  130. /* ---------------------------------------------------------------- */
  131. /* ------------------------ START CHECKPOINT  --------------------- */
  132. /* ---------------------------------------------------------------- */
  133. void Dbtup::execTUP_LCPREQ(Signal* signal) 
  134. {
  135.   CheckpointInfoPtr ciPtr;
  136.   DiskBufferSegmentInfoPtr dbsiPtr;
  137.   FragrecordPtr regFragPtr;
  138.   LocalLogInfoPtr lliPtr;
  139.   ljamEntry();
  140. //  Uint32 userptr = signal->theData[0];
  141. //  BlockReference userblockref = signal->theData[1];
  142.   ciPtr.i = signal->theData[2];
  143.   ptrCheckGuard(ciPtr, cnoOfLcpRec, checkpointInfo);
  144.   regFragPtr.i = ciPtr.p->lcpFragmentP;
  145.   ptrCheckGuard(regFragPtr, cnoOfFragrec, fragrecord);
  146. /* ---------------------------------------------------------------- */
  147. /*       ASSIGNING A VALUE DIFFERENT FROM RNIL TO CHECKPOINT VERSION*/
  148. /*       TRIGGERS THAT UNDO LOGGING WILL START FOR THIS FRAGMENT.   */
  149. /*       WE ASSIGN IT THE POINTER TO THE CHECKPOINT RECORD FOR      */
  150. /*       OPTIMISATION OF THE WRITING OF THE UNDO LOG.               */
  151. /* ---------------------------------------------------------------- */
  152.   regFragPtr.p->checkpointVersion = ciPtr.p->lcpLocalLogInfoP; /* MARK START OF UNDO LOGGING */
  153.   regFragPtr.p->maxPageWrittenInCheckpoint = getNoOfPages(regFragPtr.p);
  154.   regFragPtr.p->minPageNotWrittenInCheckpoint = 0;
  155.   ndbrequire(getNoOfPages(regFragPtr.p) > 0);
  156.   allocDataBufferSegment(signal, dbsiPtr);
  157.   dbsiPtr.p->pdxNumDataPages =  0;
  158.   dbsiPtr.p->pdxFilePage = 1;
  159.   ciPtr.p->lcpDataBufferSegmentP = dbsiPtr.i;
  160.   dbsiPtr.p->pdxCheckpointInfoP = ciPtr.i;
  161.   ciPtr.p->lcpNoOfPages = getNoOfPages(regFragPtr.p);
  162.   ciPtr.p->lcpNoCopyPagesAlloc = regFragPtr.p->noCopyPagesAlloc;
  163.   ciPtr.p->lcpEmptyPrimPage = regFragPtr.p->emptyPrimPage;
  164.   ciPtr.p->lcpThFreeFirst = regFragPtr.p->thFreeFirst;
  165.   ciPtr.p->lcpThFreeCopyFirst = regFragPtr.p->thFreeCopyFirst;
  166.   lliPtr.i = ciPtr.p->lcpLocalLogInfoP;
  167.   ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  168. /* ---------------------------------------------------------------- */
  169. /* --- PERFORM A COPY OF THE TABLE DESCRIPTOR FOR THIS FRAGMENT --- */
  170. /* ---------------------------------------------------------------- */
  171.   cprAddLogHeader(signal,
  172.                   lliPtr.p,
  173.                   ZTABLE_DESCRIPTOR,
  174.                   ciPtr.p->lcpTabPtr,
  175.                   ciPtr.p->lcpFragmentId);
  176. /* ---------------------------------------------------------------- */
  177. /*       CONTINUE WITH SAVING ACTIVE OPERATIONS AFTER A REAL-TIME   */
  178. /*       BREAK.                                                     */
  179. /* ---------------------------------------------------------------- */
  180.   ciPtr.p->lcpTmpOperPtr = regFragPtr.p->firstusedOprec;
  181.   lcpSaveCopyListLab(signal, ciPtr);
  182.   return;
  183. }//Dbtup::execTUP_LCPREQ()
  184. void Dbtup::allocDataBufferSegment(Signal* signal, DiskBufferSegmentInfoPtr& dbsiPtr) 
  185. {
  186.   UndoPagePtr regUndoPagePtr;
  187.   seizeDiskBufferSegmentRecord(dbsiPtr);
  188.   dbsiPtr.p->pdxBuffertype = COMMON_AREA_PAGES;
  189.   ndbrequire(cfirstfreeUndoSeg != RNIL);
  190.   if (cnoFreeUndoSeg == ZMIN_PAGE_LIMIT_TUP_COMMITREQ) {
  191.     EXECUTE_DIRECT(DBLQH, GSN_TUP_COM_BLOCK, signal, 1);
  192.     ljamEntry();
  193.   }//if
  194.   cnoFreeUndoSeg--;
  195.   ndbrequire(cnoFreeUndoSeg >= 0);
  196.   regUndoPagePtr.i = cfirstfreeUndoSeg;
  197.   ptrCheckGuard(regUndoPagePtr, cnoOfUndoPage, undoPage);
  198.   cfirstfreeUndoSeg = regUndoPagePtr.p->undoPageWord[ZPAGE_NEXT_POS];
  199.   regUndoPagePtr.p->undoPageWord[ZPAGE_NEXT_POS] = RNIL;
  200.   for (Uint32 i = 0; i < ZUB_SEGMENT_SIZE; i++) {
  201.     dbsiPtr.p->pdxDataPage[i] = regUndoPagePtr.i + i;
  202.   }//for
  203. }//Dbtup::allocDataBufferSegment()
  204. /* ---------------------------------------------------------------- */
  205. /* --- PERFORM A COPY OF THE ACTIVE OPERATIONS FOR THIS FRAGMENT -- */
  206. /* ---------------------------------------------------------------- */
  207. void Dbtup::lcpSaveCopyListLab(Signal* signal, CheckpointInfoPtr ciPtr) 
  208. {
  209.   FragrecordPtr regFragPtr;
  210.   LocalLogInfoPtr lliPtr;
  211.   OperationrecPtr regOpPtr;
  212.   regFragPtr.i = ciPtr.p->lcpFragmentP;
  213.   ptrCheckGuard(regFragPtr, cnoOfFragrec, fragrecord);
  214.   lliPtr.i = ciPtr.p->lcpLocalLogInfoP;
  215.   ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  216.   regOpPtr.i = ciPtr.p->lcpTmpOperPtr;
  217. /* -------------------------------------------------------------------------------- */
  218. /* TRAVERSE THE ENTIRE BLOCK OF OPERATIONS. CHECK IF THERE ARE EXISTING COPYS OF    */
  219. /* TUPLES IN THE CHECKPOINTED FRAGMENT. SAVE THOSE IN A LIST IN THE FOLLOWING FORM: */
  220. /*                                                                                  */
  221. /*    SOURCE PAGE                                                                   */
  222. /*    SOURCE INDEX                                                                  */
  223. /*    COPY PAGE                                                                     */
  224. /*    COPY INDEX                                                                    */
  225. /* -------------------------------------------------------------------------------- */
  226.   Uint32 loopCount = 0;
  227.   while ((regOpPtr.i != RNIL) && (loopCount < 50)) {
  228.     ljam();
  229.     ptrCheckGuard(regOpPtr, cnoOfOprec, operationrec);
  230.     if (regOpPtr.p->realPageId != RNIL) {
  231. /* ---------------------------------------------------------------- */
  232. // We ensure that we have actually allocated the tuple header and
  233. // also found it. Otherwise we will fill the undo log with garbage.
  234. /* ---------------------------------------------------------------- */
  235.       if (regOpPtr.p->optype == ZUPDATE || 
  236.   (regOpPtr.p->optype == ZINSERT && regOpPtr.p->deleteInsertFlag)) {
  237.         ljam();
  238.         if (regOpPtr.p->realPageIdC != RNIL) {
  239. /* ---------------------------------------------------------------- */
  240. // We ensure that we have actually allocated the tuple header copy.
  241. // Otherwise we will fill the undo log with garbage.
  242. /* ---------------------------------------------------------------- */
  243.           cprAddLogHeader(signal,
  244.                           lliPtr.p,
  245.                           ZLCPR_ABORT_UPDATE,
  246.                           ciPtr.p->lcpTabPtr,
  247.                           ciPtr.p->lcpFragmentId);
  248.           cprAddAbortUpdate(signal, lliPtr.p, regOpPtr.p);
  249.         }//if
  250.       } else if (regOpPtr.p->optype == ZINSERT) {
  251.         ljam();
  252.         cprAddUndoLogRecord(signal,
  253.                             ZLCPR_ABORT_INSERT,
  254.                             regOpPtr.p->fragPageId,
  255.                             regOpPtr.p->pageIndex,
  256.                             regOpPtr.p->tableRef,
  257.                             regOpPtr.p->fragId,
  258.                             regFragPtr.p->checkpointVersion);
  259.       } else {
  260.         ndbrequire(regOpPtr.p->optype == ZDELETE);
  261.         ljam();
  262.         cprAddUndoLogRecord(signal,
  263.                             ZINDICATE_NO_OP_ACTIVE,
  264.                             regOpPtr.p->fragPageId,
  265.                             regOpPtr.p->pageIndex,
  266.                             regOpPtr.p->tableRef,
  267.                             regOpPtr.p->fragId,
  268.                             regFragPtr.p->checkpointVersion);
  269.       }//if
  270.     }//if
  271.     loopCount++;;
  272.     regOpPtr.i = regOpPtr.p->nextOprecInList;
  273.   }//while
  274.   if (regOpPtr.i == RNIL) {
  275.     ljam();
  276.     signal->theData[0] = ciPtr.p->lcpUserptr;
  277.     sendSignal(ciPtr.p->lcpBlockref, GSN_TUP_LCPSTARTED, signal, 1, JBA);
  278.     signal->theData[0] = ZCONT_SAVE_DP;
  279.     signal->theData[1] = ciPtr.i;
  280.     sendSignal(cownref, GSN_CONTINUEB, signal, 2, JBB);
  281.   } else {
  282.     ljam();
  283.     ciPtr.p->lcpTmpOperPtr = regOpPtr.i;
  284.     signal->theData[0] = ZCONT_START_SAVE_CL;
  285.     signal->theData[1] = ciPtr.i;
  286.     sendSignal(cownref, GSN_CONTINUEB, signal, 2, JBB);
  287.   }//if
  288. }//Dbtup::lcpSaveCopyListLab()
  289. /* ---------------------------------------------------------------- */
  290. /* ------- PERFORM A COPY OF ONE DATAPAGE DURING CHECKPOINT ------- */
  291. /* ---------------------------------------------------------------- */
  292. /* THE RANGE OF DATA PAGES IS INCLUDED IN THE CHECKPOINT_INFO_PTR   */
  293. /* LAST_PAGE_TO_BUFFER ELEMENT IS INCREASED UNTIL ALL PAGES ARE     */
  294. /* COPIED TO THE DISK BUFFER. WHEN A DISK BUFFER SEGMENT IS FULL    */
  295. /* IT WILL BE WRITTEN TO DISK (TYPICALLY EACH 8:TH PAGE)            */
  296. /* ---------------------------------------------------------------- */
  297. void Dbtup::lcpSaveDataPageLab(Signal* signal, Uint32 ciIndex) 
  298. {
  299.   CheckpointInfoPtr ciPtr;
  300.   DiskBufferSegmentInfoPtr dbsiPtr;
  301.   FragrecordPtr regFragPtr;
  302.   LocalLogInfoPtr lliPtr;
  303.   UndoPagePtr undoCopyPagePtr;
  304.   PagePtr pagePtr;
  305.   ciPtr.i = ciIndex;
  306.   ptrCheckGuard(ciPtr, cnoOfLcpRec, checkpointInfo);
  307.   if (ERROR_INSERTED(4000)){
  308.     if (ciPtr.p->lcpTabPtr == c_errorInsert4000TableId) {
  309.     // Delay writing of data pages during LCP
  310.       ndbout << "Delay writing of data pages during LCP" << endl;
  311.       signal->theData[0] = ZCONT_SAVE_DP;
  312.       signal->theData[1] = ciIndex;
  313.       sendSignalWithDelay(cownref, GSN_CONTINUEB, signal, 1000, 2);
  314.       return;
  315.     }//if
  316.   }//if
  317.   if (clblPageCounter == 0) {
  318.     ljam();
  319.     signal->theData[0] = ZCONT_SAVE_DP;
  320.     signal->theData[1] = ciPtr.i;
  321.     sendSignalWithDelay(cownref, GSN_CONTINUEB, signal, 100, 2);
  322.     return;
  323.   } else {
  324.     ljam();
  325.     clblPageCounter--;
  326.   }//if
  327.   regFragPtr.i = ciPtr.p->lcpFragmentP;
  328.   ptrCheckGuard(regFragPtr, cnoOfFragrec, fragrecord);
  329.   dbsiPtr.i = ciPtr.p->lcpDataBufferSegmentP;
  330.   ptrCheckGuard(dbsiPtr, cnoOfConcurrentWriteOp, diskBufferSegmentInfo);
  331.   pagePtr.i = getRealpid(regFragPtr.p, regFragPtr.p->minPageNotWrittenInCheckpoint);
  332.   ptrCheckGuard(pagePtr, cnoOfPage, page);
  333.   ndbrequire(dbsiPtr.p->pdxNumDataPages < 16);
  334.   undoCopyPagePtr.i = dbsiPtr.p->pdxDataPage[dbsiPtr.p->pdxNumDataPages];
  335.   ptrCheckGuard(undoCopyPagePtr, cnoOfUndoPage, undoPage);
  336.   MEMCOPY_NO_WORDS(&undoCopyPagePtr.p->undoPageWord[0],
  337.                    &pagePtr.p->pageWord[0],
  338.                    ZWORDS_ON_PAGE);
  339.   regFragPtr.p->minPageNotWrittenInCheckpoint++;
  340.   dbsiPtr.p->pdxNumDataPages++;
  341.   if (regFragPtr.p->minPageNotWrittenInCheckpoint == regFragPtr.p->maxPageWrittenInCheckpoint) {
  342.     /* ---------------------------------------------------------- */
  343.     /* ALL PAGES ARE COPIED, TIME TO FINISH THE CHECKPOINT        */
  344.     /* SAVE THE END POSITIONS OF THE LOG RECORDS SINCE ALL DATA   */
  345.     /* PAGES ARE NOW SAFE ON DISK AND NO MORE LOGGING WILL APPEAR */
  346.     /* ---------------------------------------------------------- */
  347.     ljam();
  348.     lliPtr.i = ciPtr.p->lcpLocalLogInfoP;
  349.     ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  350.     regFragPtr.p->checkpointVersion = RNIL; /* UNDO LOGGING IS SHUT OFF */
  351.     lcpWriteListDataPageSegment(signal, dbsiPtr, ciPtr, false);
  352.     dbsiPtr.p->pdxOperation = CHECKPOINT_DATA_WRITE_LAST;
  353.   } else if (dbsiPtr.p->pdxNumDataPages == ZDB_SEGMENT_SIZE) {
  354.     ljam();
  355.     lcpWriteListDataPageSegment(signal, dbsiPtr, ciPtr, false);
  356.     dbsiPtr.p->pdxOperation = CHECKPOINT_DATA_WRITE;
  357.   } else {
  358.     ljam();
  359.     signal->theData[0] = ZCONT_SAVE_DP;
  360.     signal->theData[1] = ciPtr.i;
  361.     sendSignal(cownref, GSN_CONTINUEB, signal, 2, JBB);
  362.   }//if
  363. }//Dbtup::lcpSaveDataPageLab()
  364. void Dbtup::lcpWriteListDataPageSegment(Signal* signal,
  365.                                         DiskBufferSegmentInfoPtr dbsiPtr,
  366.                                         CheckpointInfoPtr ciPtr,
  367.                                         bool flushFlag) 
  368. {
  369.   Uint32 flags = 1;
  370.   cnoOfDataPagesToDiskWithoutSynch += dbsiPtr.p->pdxNumDataPages;
  371.   if ((cnoOfDataPagesToDiskWithoutSynch > MAX_PAGES_WITHOUT_SYNCH) ||
  372.       (flushFlag)) {
  373.     ljam();
  374. /* ---------------------------------------------------------------- */
  375. // To avoid synching too big chunks at a time we synch after writing
  376. // a certain number of data pages. (e.g. 2 MBytes).
  377. /* ---------------------------------------------------------------- */
  378.     cnoOfDataPagesToDiskWithoutSynch = 0;
  379.     flags |= 0x10; //Set synch flag unconditionally
  380.   }//if
  381.   signal->theData[0] = ciPtr.p->lcpDataFileHandle;
  382.   signal->theData[1] = cownref;
  383.   signal->theData[2] = dbsiPtr.i;
  384.   signal->theData[3] = flags;
  385.   signal->theData[4] = ZBASE_ADDR_UNDO_WORD;
  386.   signal->theData[5] = dbsiPtr.p->pdxNumDataPages;
  387.   signal->theData[6] = dbsiPtr.p->pdxDataPage[0];
  388.   signal->theData[7] = dbsiPtr.p->pdxFilePage;
  389.   sendSignal(NDBFS_REF, GSN_FSWRITEREQ, signal, 8, JBA);
  390.   dbsiPtr.p->pdxFilePage += dbsiPtr.p->pdxNumDataPages;
  391.   dbsiPtr.p->pdxNumDataPages = 0;
  392. }//Dbtup::lcpWriteListDataPageSegment()
  393. void Dbtup::lcpFlushLogLab(Signal* signal, CheckpointInfoPtr ciPtr) 
  394. {
  395.   DiskBufferSegmentInfoPtr oldDbsiPtr;
  396.   LocalLogInfoPtr lliPtr;
  397.   UndoPagePtr oldUndoPagePtr;
  398.   UndoPagePtr newUndoPagePtr;
  399.   lliPtr.i = ciPtr.p->lcpLocalLogInfoP;
  400.   ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  401.   oldDbsiPtr.i = lliPtr.p->lliUndoBufferSegmentP;
  402.   ptrCheckGuard(oldDbsiPtr, cnoOfConcurrentWriteOp, diskBufferSegmentInfo);
  403.   oldDbsiPtr.p->pdxNumDataPages++;
  404.   if (clblPageCounter > 0) {
  405.     ljam();
  406.     clblPageCounter--;
  407.   }//if
  408.   oldUndoPagePtr.i = lliPtr.p->lliUndoPage;
  409.   ptrCheckGuard(oldUndoPagePtr, cnoOfUndoPage, undoPage);
  410.   lcpWriteUndoSegment(signal, lliPtr.p, true);
  411.   oldDbsiPtr.p->pdxOperation = CHECKPOINT_UNDO_WRITE_FLUSH;
  412.   oldDbsiPtr.p->pdxCheckpointInfoP = ciPtr.i;
  413. /* ---------------------------------------------------------------- */
  414. /*       SINCE LAST PAGE SENT TO DISK WAS NOT FULL YET WE COPY IT   */
  415. /*       TO THE NEW LAST PAGE.                                      */
  416. /* ---------------------------------------------------------------- */
  417.   newUndoPagePtr.i = lliPtr.p->lliUndoPage;
  418.   ptrCheckGuard(newUndoPagePtr, cnoOfUndoPage, undoPage);
  419.   ndbrequire(lliPtr.p->lliUndoWord < ZWORDS_ON_PAGE);
  420.   MEMCOPY_NO_WORDS(&newUndoPagePtr.p->undoPageWord[0],
  421.                    &oldUndoPagePtr.p->undoPageWord[0],
  422.                    lliPtr.p->lliUndoWord);
  423. }//Dbtup::lcpFlushLogLab()
  424. void Dbtup::lcpFlushRestartInfoLab(Signal* signal, Uint32 ciIndex) 
  425. {
  426.   CheckpointInfoPtr ciPtr;
  427.   DiskBufferSegmentInfoPtr dbsiPtr;
  428.   LocalLogInfoPtr lliPtr;
  429.   UndoPagePtr undoCopyPagePtr;
  430.   ciPtr.i = ciIndex;
  431.   ptrCheckGuard(ciPtr, cnoOfLcpRec, checkpointInfo);
  432.   lliPtr.i = ciPtr.p->lcpLocalLogInfoP;
  433.   ptrCheckGuard(lliPtr, cnoOfParallellUndoFiles, localLogInfo);
  434.   dbsiPtr.i = ciPtr.p->lcpDataBufferSegmentP;
  435.   ptrCheckGuard(dbsiPtr, cnoOfConcurrentWriteOp, diskBufferSegmentInfo);
  436.   undoCopyPagePtr.i = dbsiPtr.p->pdxDataPage[0]; /* UNDO INFO STORED AT PAGE 0 */
  437.   ptrCheckGuard(undoCopyPagePtr, cnoOfUndoPage, undoPage);
  438.   ndbrequire(ciPtr.p->lcpNoOfPages > 0);
  439.   undoCopyPagePtr.p->undoPageWord[ZSRI_NO_OF_FRAG_PAGES_POS] = ciPtr.p->lcpNoOfPages;
  440.   undoCopyPagePtr.p->undoPageWord[ZSRI_NO_COPY_PAGES_ALLOC] = ciPtr.p->lcpNoCopyPagesAlloc;
  441.   undoCopyPagePtr.p->undoPageWord[ZSRI_EMPTY_PRIM_PAGE] = ciPtr.p->lcpEmptyPrimPage;
  442.   undoCopyPagePtr.p->undoPageWord[ZSRI_TH_FREE_FIRST] = ciPtr.p->lcpThFreeFirst;
  443.   undoCopyPagePtr.p->undoPageWord[ZSRI_TH_FREE_COPY_FIRST] = ciPtr.p->lcpThFreeCopyFirst;
  444.   undoCopyPagePtr.p->undoPageWord[ZSRI_UNDO_LOG_END_REC_ID] = lliPtr.p->lliPrevRecordId;
  445.   undoCopyPagePtr.p->undoPageWord[ZSRI_UNDO_FILE_VER] = cundoFileVersion;
  446.   if (lliPtr.p->lliUndoWord == ZUNDO_PAGE_HEADER_SIZE) {
  447.     ljam();
  448.     undoCopyPagePtr.p->undoPageWord[ZSRI_UNDO_LOG_END_PAGE_ID] = lliPtr.p->lliLogFilePage - 1;
  449.   } else {
  450.     ljam();
  451.     undoCopyPagePtr.p->undoPageWord[ZSRI_UNDO_LOG_END_PAGE_ID] = lliPtr.p->lliLogFilePage;
  452.   }//if
  453.   dbsiPtr.p->pdxNumDataPages = 1;
  454.   dbsiPtr.p->pdxFilePage = 0;
  455.   if (clblPageCounter > 0) {
  456.     ljam();
  457.     clblPageCounter--;
  458.   }//if
  459.   lcpWriteListDataPageSegment(signal, dbsiPtr, ciPtr, true);
  460.   dbsiPtr.p->pdxOperation = CHECKPOINT_DATA_WRITE_FLUSH;
  461.   return;
  462. }//Dbtup::lcpFlushRestartInfoLab()
  463. void Dbtup::lcpCompletedLab(Signal* signal, Uint32 ciIndex) 
  464. {
  465.   CheckpointInfoPtr ciPtr;
  466.   PendingFileOpenInfoPtr pfoiPtr;
  467. /* ---------------------------------------------------------------------- */
  468. /*       INSERT CODE TO CLOSE DATA FILE HERE. DO THIS BEFORE SEND CONF    */
  469. /* ---------------------------------------------------------------------- */
  470.   ciPtr.i = ciIndex;
  471.   ptrCheckGuard(ciPtr, cnoOfLcpRec, checkpointInfo);
  472.   seizePendingFileOpenInfoRecord(pfoiPtr);
  473.   pfoiPtr.p->pfoOpenType = LCP_DATA_FILE_CLOSE;
  474.   pfoiPtr.p->pfoCheckpointInfoP = ciPtr.i;
  475.   signal->theData[0] = ciPtr.p->lcpDataFileHandle;
  476.   signal->theData[1] = cownref;
  477.   signal->theData[2] = pfoiPtr.i;
  478.   signal->theData[3] = 0;
  479.   sendSignal(NDBFS_REF, GSN_FSCLOSEREQ, signal, 4, JBA);
  480.   return;
  481. }//Dbtup::lcpCompletedLab()
  482. void Dbtup::lcpClosedDataFileLab(Signal* signal, CheckpointInfoPtr ciPtr) 
  483. {
  484.   signal->theData[0] = ciPtr.p->lcpUserptr;
  485.   sendSignal(ciPtr.p->lcpBlockref, GSN_TUP_LCPCONF, signal, 1, JBB);
  486.   releaseCheckpointInfoRecord(ciPtr);
  487.   return;
  488. }//Dbtup::lcpClosedDataFileLab()
  489. /* ---------------------------------------------------------------------- */
  490. /* LCP END IS THE LAST STEP IN THE LCP PROCESS IT WILL CLOSE THE LOGFILES */
  491. /* AND RELEASE THE ALLOCATED CHECKPOINT_INFO_RECORDS                      */
  492. /* ---------------------------------------------------------------------- */
  493. void Dbtup::execEND_LCPREQ(Signal* signal) 
  494. {
  495.   DiskBufferSegmentInfoPtr dbsiPtr;
  496.   LocalLogInfoPtr lliPtr;
  497.   PendingFileOpenInfoPtr pfoiPtr;
  498.   ljamEntry();
  499.   clqhUserpointer = signal->theData[0];
  500.   clqhBlockref = signal->theData[1];
  501.   for (lliPtr.i = 0; lliPtr.i < 16; lliPtr.i++) {
  502.     ljam();
  503.     ptrAss(lliPtr, localLogInfo);
  504.     if (lliPtr.p->lliActiveLcp > 0) {
  505.       ljam();
  506.       dbsiPtr.i = lliPtr.p->lliUndoBufferSegmentP;
  507.       ptrCheckGuard(dbsiPtr, cnoOfConcurrentWriteOp, diskBufferSegmentInfo);
  508.       freeDiskBufferSegmentRecord(signal, dbsiPtr);
  509.       seizePendingFileOpenInfoRecord(pfoiPtr); /* SEIZE A NEW FILE OPEN INFO    */
  510.       pfoiPtr.p->pfoOpenType = LCP_UNDO_FILE_CLOSE;
  511.       pfoiPtr.p->pfoCheckpointInfoP = lliPtr.i;
  512.       signal->theData[0] = lliPtr.p->lliUndoFileHandle;
  513.       signal->theData[1] = cownref;
  514.       signal->theData[2] = pfoiPtr.i;
  515.       signal->theData[3] = 0;
  516.       sendSignal(NDBFS_REF, GSN_FSCLOSEREQ, signal, 4, JBA);
  517.       lliPtr.p->lliActiveLcp = 0;
  518.     }//if
  519.   }//for
  520.   return;
  521. }//Dbtup::execEND_LCPREQ()
  522. void Dbtup::lcpEndconfLab(Signal* signal) 
  523. {
  524.   LocalLogInfoPtr lliPtr;
  525.   for (lliPtr.i = 0; lliPtr.i < 16; lliPtr.i++) {
  526.     ljam();
  527.     ptrAss(lliPtr, localLogInfo);
  528.     if (lliPtr.p->lliUndoFileHandle != RNIL) {
  529.       ljam();
  530. /* ---------------------------------------------------------------------- */
  531. /*       WAIT UNTIL ALL LOG FILES HAVE BEEN CLOSED.                       */
  532. /* ---------------------------------------------------------------------- */
  533.       return;
  534.     }//if
  535.   }//for
  536.   signal->theData[0] = clqhUserpointer;
  537.   sendSignal(clqhBlockref, GSN_END_LCPCONF, signal, 1, JBB);
  538.   return;
  539. }//Dbtup::lcpEndconfLab()