filehash/ffdb_page.c
static int
_ffdb_add_key_datap_to_bucket (ffdb_htab_t* hashp, FFDB_DBT* key, 
			       ffdb_datap_t *datap, 
			       unsigned int bucket)
{
  pgno_t page, ovflpage, nextpage, tp;
  void *pagep, *opagep, *npagep;
  int needovfl, reuse;

  /* First grab a page related to this bucket */
  npagep = pagep = ffdb_get_page (hashp, bucket, HASH_BUCKET_PAGE, 
				  FFDB_CREATE, &page);
  if (!pagep) {
    fprintf (stderr, "Cannot get page for bucket %d\n", bucket);
    return -1;
  }

  needovfl = 1;
  nextpage = page;
  while (npagep) {
    /* check whether this pair should fit on this page */
    /* the following macro does not care the data part */
    if (PAIRFITS (npagep, key, dumb)) {
      _ffdb_write_key_datap_to_page (hashp, key, datap, pagep, page);
      needovfl = 0;
      /* release this page */
      ffdb_put_page (hashp, pagep, HASH_BUCKET_PAGE, 1);
      /* I am done here */
      npagep = 0;
      needovfl = 0;
    }
    else {
      nextpage = NEXT_PGNO (pagep);
      if (nextpage == INVALID_PGNO)
	npagep = 0;
      else {
	npagep = ffdb_get_page (hashp, nextpage, HASH_OVFL_PAGE, 0, &tp);
	if (!npagep) {
	  fprintf (stderr, "Cannot get overflow (expanded) page %d \n",
		   nextpage);
	  /* release the previous page */
	  ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
	  return -1;
	}
	/* release the previous page */
	ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
	
	/* assign pointers */
	pagep = npagep;
	page = nextpage;
      }
    }
  }
      
  if (needovfl) {
    reuse = 0;
    ovflpage = _ffdb_ovfl_page (hashp, &reuse);
#ifdef _FFDB_DEBUG
    fprintf (stderr, "Get an overflow page (expanded) %d for page %d\n",
	     ovflpage, page);
#endif
    /* Get this page and this page is initialized */
    opagep = ffdb_get_page (hashp, ovflpage, HASH_OVFL_PAGE,
			    FFDB_CREATE, &tp);
    if (!opagep) {
      fprintf (stderr, "Cannot allocate expanded overflow page %d for page %d\n",
	       ovflpage, page);
      /* release the previous page */
      ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
      return -1;
    }
    if (reuse) 
      _ffdb_init_page (hashp, opagep, ovflpage, HASH_OVFL_PAGE);

#ifdef _FFDB_STATISTICS
    hash_overflows++;
#endif

    /* set up correct link */
    NEXT_PGNO (pagep) = ovflpage;
    PREV_PGNO (opagep) = page;

    /* release the previous page , but the head is changed so 
     * we have to write it to disk
     */
    ffdb_put_page (hashp, pagep, TYPE(pagep), 1); 

    /* add key and data pointer to this page */
    _ffdb_write_key_datap_to_page (hashp, key, datap, opagep, ovflpage);

    /* release this page */
    ffdb_put_page (hashp, opagep, HASH_OVFL_PAGE, 1);
  }
  return 0;
}
/**
 * Add a pair of key and data pointer value to a bucket page
 * which could be the first of a few overflow pages
 *
 * The data pointer points to data pages that could be allocated
 * in previous levels
 */
Add a pair of key and data pointer value to a bucket page
which could be the first of a few overflow pages

The data pointer points to data pages that could be allocated
in previous levels
Add a pair of key and data pointer value to a bucket page which could be the first of a few overflow pages The data pointer points to data pages that could be allocated in previous levels
static int
_ffdb_add_key_datap_to_bucket (ffdb_htab_t* hashp, FFDB_DBT* key, 
			       ffdb_datap_t *datap, 
			       unsigned int bucket)
{
  pgno_t page, ovflpage, nextpage, tp;
  void *pagep, *opagep, *npagep;
  int needovfl, reuse;
  npagep = pagep = ffdb_get_page (hashp, bucket, HASH_BUCKET_PAGE, 
				  FFDB_CREATE, &page);
  if (!pagep) {
    fprintf (stderr, "Cannot get page for bucket %d\n", bucket);
    return -1;
  }
  needovfl = 1;
  nextpage = page;
  while (npagep) {
    if (PAIRFITS (npagep, key, dumb)) {
      _ffdb_write_key_datap_to_page (hashp, key, datap, pagep, page);
      needovfl = 0;
      ffdb_put_page (hashp, pagep, HASH_BUCKET_PAGE, 1);
      npagep = 0;
      needovfl = 0;
    }
    else {
      nextpage = NEXT_PGNO (pagep);
      if (nextpage == INVALID_PGNO)
	npagep = 0;
      else {
	npagep = ffdb_get_page (hashp, nextpage, HASH_OVFL_PAGE, 0, &tp);
	if (!npagep) {
	  fprintf (stderr, "Cannot get overflow (expanded) page %d \n",
		   nextpage);
	  ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
	  return -1;
	}
	ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
	pagep = npagep;
	page = nextpage;
      }
    }
  }
  if (needovfl) {
    reuse = 0;
    ovflpage = _ffdb_ovfl_page (hashp, &reuse);
#ifdef _FFDB_DEBUG
    fprintf (stderr, "Get an overflow page (expanded) %d for page %d\n",
	     ovflpage, page);
#endif
    opagep = ffdb_get_page (hashp, ovflpage, HASH_OVFL_PAGE,
			    FFDB_CREATE, &tp);
    if (!opagep) {
      fprintf (stderr, "Cannot allocate expanded overflow page %d for page %d\n",
	       ovflpage, page);
      ffdb_put_page (hashp, pagep, TYPE(pagep), 0);
      return -1;
    }
    if (reuse) 
      _ffdb_init_page (hashp, opagep, ovflpage, HASH_OVFL_PAGE);
#ifdef _FFDB_STATISTICS
    hash_overflows++;
#endif
    NEXT_PGNO (pagep) = ovflpage;
    PREV_PGNO (opagep) = page;
    ffdb_put_page (hashp, pagep, TYPE(pagep), 1); 
    _ffdb_write_key_datap_to_page (hashp, key, datap, opagep, ovflpage);
    ffdb_put_page (hashp, opagep, HASH_OVFL_PAGE, 1);
  }
  return 0;
}
static int _ffdb_add_key_datap_to_bucket ( ffdb_htab_t * hashp , FFDB_DBT * key , ffdb_datap_t * datap , unsigned int bucket ) { pgno_t page , ovflpage , nextpage , tp ; void * pagep , * opagep , * npagep ; int needovfl , reuse ; npagep = pagep = ffdb_get_page ( hashp , bucket , HASH_BUCKET_PAGE , FFDB_CREATE , & page ) ; if ( ! pagep ) { fprintf ( stderr , " \n " , bucket ) ; return -1 ; } needovfl = 1 ; nextpage = page ; while ( npagep ) { if ( PAIRFITS ( npagep , key , dumb ) ) { _ffdb_write_key_datap_to_page ( hashp , key , datap , pagep , page ) ; needovfl = 0 ; ffdb_put_page ( hashp , pagep , HASH_BUCKET_PAGE , 1 ) ; npagep = 0 ; needovfl = 0 ; } else { nextpage = NEXT_PGNO ( pagep ) ; if ( nextpage == INVALID_PGNO ) npagep = 0 ; else { npagep = ffdb_get_page ( hashp , nextpage , HASH_OVFL_PAGE , 0 , & tp ) ; if ( ! npagep ) { fprintf ( stderr , " \n " , nextpage ) ; ffdb_put_page ( hashp , pagep , TYPE ( pagep ) , 0 ) ; return -1 ; } ffdb_put_page ( hashp , pagep , TYPE ( pagep ) , 0 ) ; pagep = npagep ; page = nextpage ; } } } if ( needovfl ) { reuse = 0 ; ovflpage = _ffdb_ovfl_page ( hashp , & reuse ) ; #ifdef _FFDB_DEBUG fprintf ( stderr , " \n " , ovflpage , page ) ; #endif opagep = ffdb_get_page ( hashp , ovflpage , HASH_OVFL_PAGE , FFDB_CREATE , & tp ) ; if ( ! opagep ) { fprintf ( stderr , " \n " , ovflpage , page ) ; ffdb_put_page ( hashp , pagep , TYPE ( pagep ) , 0 ) ; return -1 ; } if ( reuse ) _ffdb_init_page ( hashp , opagep , ovflpage , HASH_OVFL_PAGE ) ; #ifdef _FFDB_STATISTICS hash_overflows ++ ; #endif NEXT_PGNO ( pagep ) = ovflpage ; PREV_PGNO ( opagep ) = page ; ffdb_put_page ( hashp , pagep , TYPE ( pagep ) , 1 ) ; _ffdb_write_key_datap_to_page ( hashp , key , datap , opagep , ovflpage ) ; ffdb_put_page ( hashp , opagep , HASH_OVFL_PAGE , 1 ) ; } return 0 ; }
Add a pair of key and data pointer value to a bucket page
 which could be the first of a few overflow pages
Add a pair of key and data pointer value to a bucket page which could be the first of a few overflow pages
/* First grab a page related to this bucket */ /* check whether this pair should fit on this page */ /* the following macro does not care the data part */ /* release this page */ /* I am done here */ /* release the previous page */ /* release the previous page */ /* assign pointers */ /* Get this page and this page is initialized */ /* release the previous page */ /* set up correct link */ /* release the previous page , but the head is changed so 
     * we have to write it to disk
     */ /* add key and data pointer to this page */ /* release this page */