LTP GCOV extension - code coverage report
Current view: directory - storage/maria - ma_preload.c
Test: mtr_and_unit.info
Date: 2009-03-05 Instrumented lines: 25
Code covered: 0.0 % Executed lines: 0

       1                 : /* Copyright (C) 2006 MySQL AB & MySQL Finland AB & TCX DataKonsult AB
       2                 : 
       3                 :    This program is free software; you can redistribute it and/or modify
       4                 :    it under the terms of the GNU General Public License as published by
       5                 :    the Free Software Foundation; version 2 of the License.
       6                 : 
       7                 :    This program is distributed in the hope that it will be useful,
       8                 :    but WITHOUT ANY WARRANTY; without even the implied warranty of
       9                 :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      10                 :    GNU General Public License for more details.
      11                 : 
      12                 :    You should have received a copy of the GNU General Public License
      13                 :    along with this program; if not, write to the Free Software
      14                 :    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
      15                 : 
      16                 : /*
      17                 :   Preload indexes into key cache
      18                 : */
      19                 : 
      20                 : #include "maria_def.h"
      21                 : 
      22                 : 
      23                 : /*
      24                 :   Preload pages of the index file for a table into the key cache
      25                 : 
      26                 :   SYNOPSIS
      27                 :     maria_preload()
      28                 :       info          open table
      29                 :       map           map of indexes to preload into key cache
      30                 :       ignore_leaves only non-leaves pages are to be preloaded
      31                 : 
      32                 :   RETURN VALUE
      33                 :     0 if a success. error code - otherwise.
      34                 : 
      35                 :   NOTES.
      36                 :     At present pages for all indexes are preloaded.
      37                 :     In future only pages for indexes specified in the key_map parameter
      38                 :     of the table will be preloaded.
      39                 :     We don't yet use preload_buff_size (we read page after page).
      40                 : */
      41                 : 
      42                 : int maria_preload(MARIA_HA *info, ulonglong key_map, my_bool ignore_leaves)
      43               0 : {
      44               0 :   ulong block_length= 0;
      45                 :   uchar *buff;
      46               0 :   MARIA_SHARE* share= info->s;
      47                 :   uint keynr;
      48               0 :   my_off_t key_file_length= share->state.state.key_file_length;
      49                 :   pgcache_page_no_t page_no, page_no_max;
      50                 :   PAGECACHE_BLOCK_LINK *page_link;
      51               0 :   DBUG_ENTER("maria_preload");
      52                 : 
      53               0 :   if (!share->state.header.keys || !maria_is_any_key_active(key_map) ||
      54                 :       (key_file_length == share->base.keystart))
      55               0 :     DBUG_RETURN(0);
      56                 : 
      57               0 :   block_length= share->pagecache->block_size;
      58                 : 
      59               0 :   if (!(buff= (uchar *) my_malloc(block_length, MYF(MY_WME))))
      60               0 :     DBUG_RETURN(my_errno= HA_ERR_OUT_OF_MEM);
      61                 : 
      62               0 :   if (flush_pagecache_blocks(share->pagecache, &share->kfile, FLUSH_RELEASE))
      63               0 :     goto err;
      64                 : 
      65                 :   /*
      66                 :     Currently when we come here all other open instances of the table have
      67                 :     been closed, and we flushed all pages of our own instance, so there
      68                 :     cannot be any page of this table in the cache. Thus my_pread() would be
      69                 :     safe. But in the future, we will allow more concurrency during
      70                 :     preloading, so we use pagecache_read() instead of my_pread() because we
      71                 :     observed that on some Linux, concurrent pread() and pwrite() (which
      72                 :     could be from a page eviction by another thread) to the same page can
      73                 :     make pread() see an half-written page.
      74                 :     In this future, we should find a way to read state.key_file_length
      75                 :     reliably, handle concurrent shrinks (delete_all_rows()) etc.
      76                 :   */
      77                 :   for ((page_no= share->base.keystart / block_length),
      78               0 :          (page_no_max= key_file_length / block_length);
      79               0 :        page_no < page_no_max; page_no++)
      80                 :   {
      81                 :     /**
      82                 :       @todo instead of reading pages one by one we could have a call
      83                 :       pagecache_read_several_pages() which does a single my_pread() for many
      84                 :       consecutive pages (like the my_pread() in mi_preload()).
      85                 :     */
      86               0 :     if (pagecache_read(share->pagecache, &share->kfile, page_no,
      87                 :                        DFLT_INIT_HITS, buff, share->page_type,
      88                 :                        PAGECACHE_LOCK_WRITE, &page_link) == NULL)
      89               0 :       goto err;
      90               0 :     keynr= _ma_get_keynr(share, buff);
      91               0 :     if (((ignore_leaves && !_ma_test_if_nod(share, buff)) ||
      92                 :          keynr == MARIA_DELETE_KEY_NR ||
      93                 :          !(key_map & ((ulonglong) 1 << keynr))) &&
      94                 :         (pagecache_pagelevel(page_link) == DFLT_INIT_HITS))
      95                 :     {
      96                 :       /*
      97                 :         This page is not interesting, and (last condition above) we are the
      98                 :         ones who put it in the cache, so nobody else is interested in it.
      99                 :       */
     100               0 :       if (pagecache_delete_by_link(share->pagecache, page_link,
     101                 :                                    PAGECACHE_LOCK_LEFT_WRITELOCKED, FALSE))
     102                 :         goto err;
     103                 :     }
     104                 :     else /* otherwise it stays in cache: */
     105               0 :       pagecache_unlock_by_link(share->pagecache, page_link,
     106                 :                                PAGECACHE_LOCK_WRITE_UNLOCK, PAGECACHE_UNPIN,
     107                 :                                LSN_IMPOSSIBLE, LSN_IMPOSSIBLE, FALSE, FALSE);
     108                 :   }
     109                 : 
     110               0 :   my_free(buff, MYF(0));
     111               0 :   DBUG_RETURN(0);
     112                 : 
     113               0 : err:
     114               0 :   my_free(buff, MYF(MY_ALLOW_ZERO_PTR));
     115               0 :   DBUG_RETURN(my_errno= errno);
     116                 : }

Generated by: LTP GCOV extension version 1.4