List:Internals« Previous MessageNext Message »
From:jonas.oreland Date:March 29 2005 10:20am
Subject:bk commit into 5.1-ndb tree (joreland:1.1800)
View as plain text  
Below is the list of changes that have just been committed into a local
5.1-ndb repository of jonas. When jonas does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html

ChangeSet
  1.1800 05/03/29 10:20:08 joreland@stripped +2 -0
  wl1870 - ndb diskdata
    cut tail of undo log at LCP

  ndb/src/kernel/blocks/lgman.hpp
    1.19 05/03/29 10:20:05 joreland@stripped +11 -17
    Impl. cutting of log tail (on LCP)

  ndb/src/kernel/blocks/lgman.cpp
    1.23 05/03/29 10:20:05 joreland@stripped +162 -65
    Impl. cutting of log tail (on LCP)

# This is a BitKeeper patch.  What follows are the unified diffs for the
# set of deltas contained in the patch.  The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User:	joreland
# Host:	eel.hemma.oreland.se
# Root:	/home/jonas/src/mysql-5.1-ndb-dd

--- 1.22/ndb/src/kernel/blocks/lgman.cpp	Wed Mar 23 07:45:05 2005
+++ 1.23/ndb/src/kernel/blocks/lgman.cpp	Tue Mar 29 10:20:05 2005
@@ -109,13 +109,19 @@
   jamEntry();
 
   Uint32 type= signal->theData[0];
+  Uint32 ptrI = signal->theData[1];
   switch(type){
-  case LgmanContinueB::CUT_LOG_TAIL:
   case LgmanContinueB::FILTER_LOG:
     break;
+  case LgmanContinueB::CUT_LOG_TAIL:
+  {
+    Ptr<Logfile_group> ptr;
+    m_logfile_group_pool.getPtr(ptr, ptrI);
+    cut_log_tail(signal, ptr);
+    return;
+  }
   case LgmanContinueB::FLUSH_LOG:
   {
-    Uint32 ptrI = signal->theData[1];
     Ptr<Logfile_group> ptr;
     m_logfile_group_pool.getPtr(ptr, ptrI);
     flush_log(signal, ptr);
@@ -123,7 +129,6 @@
   }
   case LgmanContinueB::PROCESS_LOG_BUFFER_WAITERS:
   {
-    Uint32 ptrI = signal->theData[1];
     Ptr<Logfile_group> ptr;
     m_logfile_group_pool.getPtr(ptr, ptrI);
     process_log_buffer_waiters(signal, ptr);
@@ -365,6 +370,9 @@
   meta.release(ptr);
 }
 
+#define HEAD 0
+#define TAIL 1
+
 void
 Lgman::execFSOPENCONF(Signal* signal)
 {
@@ -380,6 +388,7 @@
 
   LocalDLFifoList<Undofile> free(m_file_pool, lg_ptr.p->m_files);
   LocalDLList<Undofile> meta(m_file_pool, lg_ptr.p->m_meta_files);
+  bool first= free.isEmpty();
   meta.remove(ptr);
   free.add(ptr);
 
@@ -387,8 +396,6 @@
   Uint32 senderData = ptr.p->m_create.m_senderData;
 
   ptr.p->m_online.m_fd = fd;
-  ptr.p->m_online.m_tail_offset = 0;
-  ptr.p->m_online.m_head_offset = 0;
   ptr.p->m_online.m_outstanding = 0;
   ptr.p->m_state = Undofile::FS_ONLINE;
   
@@ -401,16 +408,19 @@
   }
 
   Uint64 add= ptr.p->m_file_size - 1;
-  lg_ptr.p->m_free_file_words += add * GLOBAL_PAGE_SIZE_WORDS;
+  lg_ptr.p->m_free_file_words += add * File_formats::UNDO_PAGE_WORDS;
 
-  if(lg_ptr.p->m_current_file_ptr_i == RNIL)
+  if(first)
   {
     jam();
-    lg_ptr.p->m_current_file_ptr_i= ptr.i;
+    
+    Buffer_idx tmp= { ptr.i, 0 };
+    lg_ptr.p->m_file_pos[HEAD] = lg_ptr.p->m_file_pos[TAIL] = tmp;
+    
     /**
-     * Keep 1 free page just in case
+     * Init log tail pointer
      */
-    lg_ptr.p->m_free_file_words -= GLOBAL_PAGE_SIZE_WORDS;
+    lg_ptr.p->m_lcp[0] = lg_ptr.p->m_lcp[1] = lg_ptr.p->m_lcp[2] = tmp;
   }
 }
 
@@ -433,12 +443,19 @@
   m_last_written_lsn = 0;
   m_current_sync_lsn = 0;
   
-  m_current_file_ptr_i = RNIL;
+  m_file_pos[0].m_ptr_i= m_file_pos[1].m_ptr_i = RNIL;
+
+  m_free_file_words = 0;
   m_free_buffer_words = 0;
   m_pos[READER].m_current_page.m_ptr_i = RNIL;   // { m_buffer_pages, idx }
   m_pos[READER].m_current_pos.m_ptr_i = RNIL;    // { page ptr.i, m_words_used}
   m_pos[WRITER].m_current_page.m_ptr_i = RNIL;   // { m_buffer_pages, idx }
   m_pos[WRITER].m_current_pos.m_ptr_i = RNIL;    // { page ptr.i, m_words_used}
+
+  m_lcp[2].m_ptr_i= RNIL;
+  m_lcp[2].m_idx= ~0;
+  
+  m_lcp[0] = m_lcp[1] = m_lcp[2];
 }
 
 bool
@@ -547,7 +564,7 @@
   pages = (pages << 32) | req->file_size_lo;
   pages /= GLOBAL_PAGE_SIZE;
   m_file_size = pages;
-  
+
   m_create.m_senderRef = req->senderRef; // During META
   m_create.m_senderData = req->senderData; // During META
   m_create.m_logfile_group_id = req->filegroup_id;
@@ -655,10 +672,12 @@
   assert(total_free >= sz);
   Uint32 pos= ptr.p->m_pos[WRITER].m_current_pos.m_idx;
   Uint32 free= File_formats::UNDO_PAGE_WORDS - pos;
+
   if(sz <= free)
   {
 next:
     // fits this page wo/ problem
+    ndbassert(total_free >= sz);
     ptr.p->m_free_buffer_words = total_free - sz;
     ptr.p->m_pos[WRITER].m_current_pos.m_idx = pos + sz;
     return ((File_formats::Undofile::Undo_page*)pageP)->m_data + pos;
@@ -674,6 +693,12 @@
   undo->m_page_header.m_page_lsn_hi = lsn >> 32;
   undo->m_data[File_formats::UNDO_PAGE_WORDS-1]= 
     File_formats::Undofile::UNDO_NOOP << 16 | free;
+
+  /**
+   * Update free space with extra NOOP
+   */
+  ndbassert(ptr.p->m_free_file_words >= free);
+  ptr.p->m_free_file_words -= free;
   
   pos= 0;
   assert(total_free >= free);
@@ -764,8 +789,6 @@
       m_lgman->process_log_buffer_waiters(signal, ptr);
     }
     
-    ndbout_c("in log buffer wait queue");
-
     return 0;
   }
   return -1;
@@ -790,9 +813,17 @@
  
   jamEntry();
 
-  if(ptr.p->m_current_file_ptr_i == RNIL ||
+  if(ptr.p->m_file_pos[HEAD].m_ptr_i == RNIL ||
      reader.m_current_page == writer.m_current_page)
   {
+#if 0
+    ndbout_c("ptr.p->m_file_pos[HEAD].m_ptr_i= %x", 
+	     ptr.p->m_file_pos[HEAD].m_ptr_i);
+    ndbout_c("reader.m_current_page: %d %d writer.m_current_page: %d %d",
+	     reader.m_current_page.m_ptr_i, reader.m_current_page.m_idx,
+	     writer.m_current_page.m_ptr_i, writer.m_current_page.m_idx);
+#endif
+
     signal->theData[0] = LgmanContinueB::FLUSH_LOG;
     signal->theData[1] = ptr.i;
     sendSignalWithDelay(reference(), GSN_CONTINUEB, signal, 100, 2);
@@ -877,16 +908,16 @@
 	reader.m_current_pos.m_ptr_i += cnt;
       }
     }
-    
+
     tot += cnt;
     ptr.p->m_free_buffer_words += (cnt * File_formats::UNDO_PAGE_WORDS);
   }
-  
+
   ptr.p->m_pos[READER]= reader;
   
   signal->theData[0] = LgmanContinueB::FLUSH_LOG;
   signal->theData[1] = ptr.i;
-  sendSignalWithDelay(reference(), GSN_CONTINUEB, signal, tot*100, 2);
+  sendSignal(reference(), GSN_CONTINUEB, signal, 2, JBB);
 
   if(tot > 0 && !ptr.p->m_log_buffer_waiters.isEmpty())
   {
@@ -898,7 +929,6 @@
 void
 Lgman::process_log_buffer_waiters(Signal* signal, Ptr<Logfile_group> ptr)
 {
-  printf("process_log_buffer_waiters -");
   Uint32 free_buffer= ptr.p->m_free_buffer_words;
   LocalDLFifoList<Log_buffer_waiter> 
     list(m_log_buffer_waiter_pool, ptr.p->m_log_buffer_waiters);
@@ -918,87 +948,77 @@
     SimulatedBlock* b = globalData.getBlock(block);
     b->execute(signal, waiter.p->m_callback, 0);
 
-    printf("removing from list - ");
     list.release(waiter);
   }
   
   if(removed && !list.isEmpty())
   {
-    ndbout_c(" - continueb ");
     signal->theData[0] = LgmanContinueB::PROCESS_LOG_BUFFER_WAITERS;
     signal->theData[1] = ptr.i;
     sendSignal(reference(), GSN_CONTINUEB, signal, 2, JBB);
   }
-
-  ndbout_c("");
 }
 
 Uint32
 Lgman::write_log_pages(Signal* signal, Ptr<Logfile_group> ptr,
-		       Uint32 pageId, Uint32 pages)
+		       Uint32 pageId, Uint32 in_pages)
 {
-  assert(pages);
+  assert(in_pages);
   Ptr<Undofile> filePtr;
-  m_file_pool.getPtr(filePtr, ptr.p->m_current_file_ptr_i);
+  Buffer_idx head= ptr.p->m_file_pos[HEAD];
+  Buffer_idx tail= ptr.p->m_file_pos[TAIL];
+  m_file_pool.getPtr(filePtr, head.m_ptr_i);
   
-  if(filePtr.p->m_online.m_outstanding > 0 || 
-     filePtr.p->m_state & Undofile::FS_FULL)
+  if(filePtr.p->m_online.m_outstanding > 0)
   {
     jam();
     return 0;
   }
-
+  
   filePtr.p->m_online.m_outstanding++;
   
   Uint32 sz= filePtr.p->m_file_size - 1; // skip zero
-  Uint32 head= filePtr.p->m_online.m_head_offset;
-  Uint32 tail= filePtr.p->m_online.m_tail_offset;
-  Uint32 free= head >= tail ? sz - head : tail - head;
+  Uint32 max, pages= in_pages;
+
+  if(!(head.m_ptr_i == tail.m_ptr_i && head.m_idx < tail.m_idx))
+  {
+    max= sz - head.m_idx;
+  }
+  else
+  {
+    max= tail.m_idx - head.m_idx;
+  }
   
   FsReadWriteReq* req= (FsReadWriteReq*)signal->getDataPtrSend();
   req->filePointer = filePtr.p->m_online.m_fd;
   req->userReference = reference();
   req->userPointer = filePtr.i;
-  req->varIndex = 1+head; // skip zero page
+  req->varIndex = 1+head.m_idx; // skip zero page
   req->numberOfPages = pages;
   req->data.pageData[0] = pageId;
   req->operationFlag = 0;
   FsReadWriteReq::setFormatFlag(req->operationFlag, 
 				FsReadWriteReq::fsFormatGlobalPage);
 
-  Ptr<GlobalPage> pagePtr;
-  Uint32 cnt;
-  if(head + pages < free)
+  if(max > pages)
   {
     jam();
-    cnt= pages;
-    filePtr.p->m_online.m_head_offset = head + pages;
+    max= pages;
+    head.m_idx += max;
+    ptr.p->m_file_pos[HEAD] = head;  
+    
     sendSignal(NDBFS_REF, GSN_FSWRITEREQ, signal, 
 	       FsReadWriteReq::FixedLength + 1, JBA);
-
+    
   }
   else
   {
     jam();
-    cnt= free > pages ? pages : free;
-    
-    req->numberOfPages = cnt;
-    filePtr.p->m_online.m_head_offset = head + cnt;
+    req->numberOfPages = max;
     FsReadWriteReq::setSyncFlag(req->operationFlag, 1);
     
     sendSignal(NDBFS_REF, GSN_FSWRITEREQ, signal, 
 	       FsReadWriteReq::FixedLength + 1, JBA);
-
-    if(((head + cnt) % sz) == tail)
-    {
-      jam();
-      filePtr.p->m_state |= Undofile::FS_FULL;
-    }
-  }
-  
-  if(head + cnt >= sz)
-  {
-    jam();
     
     Ptr<Undofile> next = filePtr;
     LocalDLFifoList<Undofile> files(m_file_pool, ptr.p->m_files);
@@ -1007,16 +1027,16 @@
       jam();
       files.first(next);
     }
-    ptr.p->m_current_file_ptr_i = next.i;
+    ndbout_c("changing file from %d to %d", filePtr.i, next.i);
 
-    if(cnt != pages)
-    {
-      jam();
-      return cnt + write_log_pages(signal, ptr, pageId + cnt, pages - cnt);
-    }
+    head.m_idx= 0;
+    head.m_ptr_i= next.i;
+    ptr.p->m_file_pos[HEAD] = head;
+    if(max < pages)
+      max += write_log_pages(signal, ptr, pageId + max, pages - max);
   }
-  
-  return cnt;
+
+  return max;
 }
 
 void
@@ -1036,6 +1056,8 @@
 
   ndbassert(filePtr.p->m_online.m_outstanding);
   filePtr.p->m_online.m_outstanding--;
+
+  
 }
 
 void
@@ -1048,19 +1070,85 @@
 
   Ptr<Logfile_group> ptr;
   m_logfile_group_list.first(ptr);
+
+  if(!ptr.isNull())
+  {
+    signal->theData[0] = LgmanContinueB::CUT_LOG_TAIL;
+    signal->theData[1] = ptr.i;
+    sendSignal(reference(), GSN_CONTINUEB, signal, 2, JBB);
+  }
   
   Uint32 undo[2];
   undo[0] = lcp_id;
   undo[1] = File_formats::Undofile::UNDO_LCP << 16 | 8;
+
   while(!ptr.isNull())
   {
     Uint32 *dst= get_log_buffer(ptr, 2);
     memcpy(dst, undo, 8);
+
+    ptr.p->m_lcp[0] = ptr.p->m_lcp[1];
+    ptr.p->m_lcp[1] = ptr.p->m_lcp[2];
+    ptr.p->m_lcp[2] = ptr.p->m_file_pos[HEAD];
+    
+    if(0)
+      ndbout_c
+	("execLCP_FRAG_ORD (%d %d) (%d %d) (%d %d) free pages: %d", 
+	 ptr.p->m_lcp[0].m_ptr_i, ptr.p->m_lcp[0].m_idx,
+	 ptr.p->m_lcp[1].m_ptr_i, ptr.p->m_lcp[1].m_idx,
+	 ptr.p->m_lcp[2].m_ptr_i, ptr.p->m_lcp[2].m_idx,
+	 (ptr.p->m_free_file_words / File_formats::UNDO_PAGE_WORDS));
+    
     m_logfile_group_list.next(ptr);
   }
 }
 
 void
+Lgman::cut_log_tail(Signal* signal, Ptr<Logfile_group> ptr)
+{
+  Buffer_idx tmp= ptr.p->m_lcp[0];
+  Ptr<Undofile> filePtr;
+  m_file_pool.getPtr(filePtr, tmp.m_ptr_i);
+  Buffer_idx tail= ptr.p->m_file_pos[TAIL];
+
+  bool done= true;
+  if(!(tmp == tail))
+  {
+    if(tmp.m_ptr_i == tail.m_ptr_i && tail.m_idx < tmp.m_idx)
+    {
+      Uint32 free= tmp.m_idx - tail.m_idx; 
+      ptr.p->m_free_file_words += free * File_formats::UNDO_PAGE_WORDS;
+      ptr.p->m_file_pos[TAIL] = tmp;
+    }
+    else
+    {
+      Uint32 free= filePtr.p->m_file_size - tail.m_idx - 1;
+      ptr.p->m_free_file_words += free * File_formats::UNDO_PAGE_WORDS;
+      
+      Ptr<Undofile> next = filePtr;
+      LocalDLFifoList<Undofile> files(m_file_pool, ptr.p->m_files);
+      if(!files.next(next))
+      {
+	jam();
+	files.first(next);
+      }
+      
+      tmp.m_idx= 0;
+      tmp.m_ptr_i= next.i;
+      ptr.p->m_file_pos[TAIL] = tmp;
+      done= false;
+    }
+  } 
+     
+  if(!done || m_logfile_group_list.next(ptr))
+  {
+    signal->theData[0] = LgmanContinueB::CUT_LOG_TAIL;
+    signal->theData[1] = ptr.i;
+    sendSignal(reference(), GSN_CONTINUEB, signal, 2, JBB);
+  }
+}
+
+void
 Lgman::execSUB_GCP_COMPLETE_REP(Signal* signal)
 {
   jamEntry();
@@ -1087,7 +1175,8 @@
   Logfile_group key;
   key.m_logfile_group_id= ref;
   Ptr<Logfile_group> ptr;
-  if(m_logfile_group_hash.find(ptr, key) && ptr.p->m_free_file_words >= words)
+  if(m_logfile_group_hash.find(ptr, key) && 
+     ptr.p->m_free_file_words >= words + File_formats::UNDO_PAGE_WORDS)
   {
     ptr.p->m_free_file_words -= words;
     return 0;
@@ -1102,7 +1191,15 @@
 }
 
 int
-Lgman::free_log_space(Uint32 logfile_group_ref, Uint32 words)
+Lgman::free_log_space(Uint32 ref, Uint32 words)
 {
-  return 0;
+  Logfile_group key;
+  key.m_logfile_group_id= ref;
+  Ptr<Logfile_group> ptr;
+  if(m_logfile_group_hash.find(ptr, key))
+  {
+    ptr.p->m_free_file_words += words;
+    return 0;
+  }
+  return -1;
 }

--- 1.18/ndb/src/kernel/blocks/lgman.hpp	Tue Mar 22 15:53:38 2005
+++ 1.19/ndb/src/kernel/blocks/lgman.hpp	Tue Mar 29 10:20:05 2005
@@ -57,13 +57,6 @@
   void execSUB_GCP_COMPLETE_REP(Signal*);
 
 public:
-  struct Lcp_record 
-  {
-    Uint32 m_file_ptr_i;
-    Uint32 m_page_no; // In file
-    Uint64 m_lsn;
-  };
-
   struct Log_buffer_waiter
   {
     Uint32 m_size;
@@ -92,14 +85,11 @@
       FS_CREATING = 0x1  // File is being created
       ,FS_DROPPING = 0x2 // File is being dropped
       ,FS_ONLINE   = 0x4 // File is online
-      ,FS_FULL     = 0x8 // File is full (head == tail)
     };
     
     union {
       struct {
 	Uint32 m_fd; // When speaking to NDBFS
-	Uint32 m_tail_offset; // in pages
-	Uint32 m_head_offset; // in pages
 	Uint32 m_outstanding; // requests
       } m_online;
       struct {
@@ -138,6 +128,11 @@
     }
   };
 
+  struct Lcp_record 
+  {
+    Buffer_idx m_pos;
+  };
+
   struct Logfile_group
   {
     Logfile_group(){}
@@ -154,10 +149,10 @@
     Uint64 m_last_written_lsn;
     Uint64 m_current_sync_lsn;
 
-    Lcp_record m_lcp[2];
-
-    Uint32 m_current_file_ptr_i;        // Current file
-    Uint64 m_free_file_words;           // Free words in logfile group 
+    Buffer_idx m_lcp[3]; // 0 is cut, 1 is saved, 2 is current
+    Buffer_idx m_file_pos[2]; // 0 tail, 1 head = { file_ptr_i, page_no }
+    Uint64 m_free_file_words; // Free words in logfile group 
+    
     DLFifoList<Undofile>::Head m_files; // Files in log
     DLList<Undofile>::Head m_meta_files;// Files being created or dropped
     
@@ -165,7 +160,7 @@
     DLFifoList<Log_buffer_waiter>::Head m_log_buffer_waiters;
     Page_map::Head m_buffer_pages; // Pairs of { ptr.i, count }
     struct Position {
-      Buffer_idx m_current_page;   // { m_buffer_pages, idx }
+      Buffer_idx m_current_page;   // { m_buffer_pages, left in range }
       Buffer_idx m_current_pos;    // { page ptr.i, m_words_used }
     } m_pos[2]; // 0 is reader (lgman) 1 is writer (tup)
 
@@ -211,8 +206,7 @@
   void process_log_buffer_waiters(Signal* signal, Ptr<Logfile_group>);
   Uint32 next_page(Logfile_group* ptrP, Uint32 i);
   
-  void cut_log_tail(Signal*, Ptr<Logfile_group> ptr, Uint32 lcp_id);
-  
+  void cut_log_tail(Signal*, Ptr<Logfile_group> ptr);
   void open_file(Signal*, Ptr<Undofile>, Uint32 requestInfo);
 
   void flush_log(Signal*, Ptr<Logfile_group>);
Thread
bk commit into 5.1-ndb tree (joreland:1.1800)jonas.oreland29 Mar