/*
 *  Copyright 2000 by Hans Reiser, licensing governed by reiserfs/README
 */

/*
 *  Written by Anatoly P. Pinchuk pap@namesys.botik.ru
 *  Programm System Institute
 *  Pereslavl-Zalessky Russia
 */

/*
 *  This file contains functions dealing with S+tree
 *
 * B_IS_IN_TREE
 * copy_item_head
 * comp_short_keys
 * comp_keys
 * comp_short_le_keys
 * le_key2cpu_key
 * comp_le_keys
 * bin_search
 * get_lkey
 * get_rkey
 * key_in_buffer
 * decrement_bcount
 * decrement_counters_in_path
 * reiserfs_check_path
 * pathrelse_and_restore
 * pathrelse
 * search_by_key_reada
 * search_by_key
 * search_for_position_by_key
 * comp_items
 * prepare_for_direct_item
 * prepare_for_direntry_item
 * prepare_for_delete_or_cut
 * calc_deleted_bytes_number
 * init_tb_struct
 * padd_item
 * reiserfs_delete_item
 * reiserfs_delete_solid_item
 * reiserfs_delete_object
 * maybe_indirect_to_direct
 * indirect_to_direct_roll_back
 * reiserfs_cut_from_item
 * truncate_directory
 * reiserfs_do_truncate
 * reiserfs_paste_into_item
 * reiserfs_insert_item
 */

#include <linux/config.h>
#include <linux/time.h>
#include <linux/string.h>
#include <linux/pagemap.h>
#include <linux/reiserfs_fs.h>
#include <linux/smp_lock.h>
#include <linux/buffer_head.h>
#include <linux/quotaops.h>

/* Does the buffer contain a disk block which is in the tree. */
inline int B_IS_IN_TREE (const struct buffer_head * p_s_bh)
{

  RFALSE( B_LEVEL (p_s_bh) > MAX_HEIGHT,
	  "PAP-1010: block (%b) has too big level (%z)", p_s_bh, p_s_bh);

  return ( B_LEVEL (p_s_bh) != FREE_LEVEL );
}

//
// to gets item head in le form
//
inline void copy_item_head(struct item_head * p_v_to, 
			   const struct item_head * p_v_from)
{
  memcpy (p_v_to, p_v_from, IH_SIZE);
}


/* k1 is pointer to on-disk structure which is stored in little-endian
   form. k2 is pointer to cpu variable. For key of items of the same
   object this returns 0.
   Returns: -1 if key1 < key2 
   0 if key1 == key2
   1 if key1 > key2 */
inline int  comp_short_keys (const struct reiserfs_key * le_key,
			     const struct cpu_key * cpu_key)
{
  __u32 n;
  n = le32_to_cpu(le_key->k_dir_id);
  if (n < cpu_key->on_disk_key.k_dir_id)
      return -1;
  if (n > cpu_key->on_disk_key.k_dir_id)
      return 1;
  n = le32_to_cpu(le_key->k_objectid);
  if (n < cpu_key->on_disk_key.k_objectid)
      return -1;
  if (n > cpu_key->on_disk_key.k_objectid)
      return 1;
  return 0;
}

/* k1 is pointer to on-disk structure which is stored in little-endian
   form. k2 is pointer to cpu variable.
   Compare keys using all 4 key fields.
   Returns: -1 if key1 < key2 0
   if key1 = key2 1 if key1 > key2 */
static inline int  comp_keys (const struct reiserfs_key * le_key, const struct cpu_key * cpu_key)
{
  int retval;

  retval = comp_short_keys (le_key, cpu_key);
  if (retval)
      return retval;
  if (le_key_k_offset (le_key_version(le_key), le_key) < cpu_key_k_offset (cpu_key))
      return -1;
  if (le_key_k_offset (le_key_version(le_key), le_key) > cpu_key_k_offset (cpu_key))
      return 1;

  if (cpu_key->key_length == 3)
      return 0;

  /* this part is needed only when tail conversion is in progress */
  if (le_key_k_type (le_key_version(le_key), le_key) < cpu_key_k_type (cpu_key))
    return -1;

  if (le_key_k_type (le_key_version(le_key), le_key) > cpu_key_k_type (cpu_key))
    return 1;

  return 0;
}


inline int comp_short_le_keys (const struct reiserfs_key * key1, const struct reiserfs_key * key2)
{
  __u32 * p_s_1_u32, * p_s_2_u32;
  int n_key_length = REISERFS_SHORT_KEY_LEN;

  p_s_1_u32 = (__u32 *)key1;
  p_s_2_u32 = (__u32 *)key2;
  for( ; n_key_length--; ++p_s_1_u32, ++p_s_2_u32 ) {
    if ( le32_to_cpu (*p_s_1_u32) < le32_to_cpu (*p_s_2_u32) )
      return -1;
    if ( le32_to_cpu (*p_s_1_u32) > le32_to_cpu (*p_s_2_u32) )
      return 1;
  }
  return 0;
}

inline void le_key2cpu_key (struct cpu_key * to, const struct reiserfs_key * from)
{
    int version;
    to->on_disk_key.k_dir_id = le32_to_cpu (from->k_dir_id);
    to->on_disk_key.k_objectid = le32_to_cpu (from->k_objectid);
    
    // find out version of the key
    version = le_key_version (from);
    to->version = version;
    to->on_disk_key.k_offset = le_key_k_offset(version, from);
    to->on_disk_key.k_type = le_key_k_type(version, from);
}



// this does not say which one is bigger, it only returns 1 if keys
// are not equal, 0 otherwise
inline int comp_le_keys (const struct reiserfs_key * k1, const struct reiserfs_key * k2)
{
    return memcmp (k1, k2, sizeof (struct reiserfs_key));
}

/**************************************************************************
 *  Binary search toolkit function                                        *
 *  Search for an item in the array by the item key                       *
 *  Returns:    1 if found,  0 if not found;                              *
 *        *p_n_pos = number of the searched element if found, else the    *
 *        number of the first element that is larger than p_v_key.        *
 **************************************************************************/
/* For those not familiar with binary search: n_lbound is the leftmost item that it
 could be, n_rbound the rightmost item that it could be.  We examine the item
 halfway between n_lbound and n_rbound, and that tells us either that we can increase
 n_lbound, or decrease n_rbound, or that we have found it, or if n_lbound <= n_rbound that
 there are no possible items, and we have not found it. With each examination we
 cut the number of possible items it could be by one more than half rounded down,
 or we find it. */
static inline	int bin_search (
              const void * p_v_key, /* Key to search for.                   */
	      const void * p_v_base,/* First item in the array.             */
	      int       p_n_num,    /* Number of items in the array.        */
	      int       p_n_width,  /* Item size in the array.
				       searched. Lest the reader be
				       confused, note that this is crafted
				       as a general function, and when it
				       is applied specifically to the array
				       of item headers in a node, p_n_width
				       is actually the item header size not
				       the item size.                      */
	      int     * p_n_pos     /* Number of the searched for element. */
            ) {
    int   n_rbound, n_lbound, n_j;

   for ( n_j = ((n_rbound = p_n_num - 1) + (n_lbound = 0))/2; n_lbound <= n_rbound; n_j = (n_rbound + n_lbound)/2 )
     switch( comp_keys((struct reiserfs_key *)((char * )p_v_base + n_j * p_n_width), (struct cpu_key *)p_v_key) )  {
     case -1: n_lbound = n_j + 1; continue;
     case  1: n_rbound = n_j - 1; continue;
     case  0: *p_n_pos = n_j;     return ITEM_FOUND; /* Key found in the array.  */
        }

    /* bin_search did not find given key, it returns position of key,
        that is minimal and greater than the given one. */
    *p_n_pos = n_lbound;
    return ITEM_NOT_FOUND;
}

#ifdef CONFIG_REISERFS_CHECK
extern struct tree_balance * cur_tb;
#endif



/* Minimal possible key. It is never in the tree. */
const struct reiserfs_key  MIN_KEY = {0, 0, {{0, 0},}};

/* Maximal possible key. It is never in the tree. */
const struct reiserfs_key  MAX_KEY = {
	__constant_cpu_to_le32(0xffffffff),
	__constant_cpu_to_le32(0xffffffff),
	{{__constant_cpu_to_le32(0xffffffff),
	__constant_cpu_to_le32(0xffffffff)},}
};


/* Get delimiting key of the buffer by looking for it in the buffers in the path, starting from the bottom
   of the path, and going upwards.  We must check the path's validity at each step.  If the key is not in
   the path, there is no delimiting key in the tree (buffer is first or last buffer in tree), and in this
   case we return a special key, either MIN_KEY or MAX_KEY. */
static inline	const struct  reiserfs_key * get_lkey  (
	                const struct path         * p_s_chk_path,
                        const struct super_block  * p_s_sb
                      ) {
  int                   n_position, n_path_offset = p_s_chk_path->path_length;
  struct buffer_head  * p_s_parent;
  
  RFALSE( n_path_offset < FIRST_PATH_ELEMENT_OFFSET, 
	  "PAP-5010: invalid offset in the path");

  /* While not higher in path than first element. */
  while ( n_path_offset-- > FIRST_PATH_ELEMENT_OFFSET ) {

    RFALSE( ! buffer_uptodate(PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset)),
	    "PAP-5020: parent is not uptodate");

    /* Parent at the path is not in the tree now. */
    if ( ! B_IS_IN_TREE(p_s_parent = PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset)) )
      return &MAX_KEY;
    /* Check whether position in the parent is correct. */
    if ( (n_position = PATH_OFFSET_POSITION(p_s_chk_path, n_path_offset)) > B_NR_ITEMS(p_s_parent) )
       return &MAX_KEY;
    /* Check whether parent at the path really points to the child. */
    if ( B_N_CHILD_NUM(p_s_parent, n_position) !=
	 PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset + 1)->b_blocknr )
      return &MAX_KEY;
    /* Return delimiting key if position in the parent is not equal to zero. */
    if ( n_position )
      return B_N_PDELIM_KEY(p_s_parent, n_position - 1);
  }
  /* Return MIN_KEY if we are in the root of the buffer tree. */
  if ( PATH_OFFSET_PBUFFER(p_s_chk_path, FIRST_PATH_ELEMENT_OFFSET)->b_blocknr ==
       SB_ROOT_BLOCK (p_s_sb) )
    return &MIN_KEY;
  return  &MAX_KEY;
}


/* Get delimiting key of the buffer at the path and its right neighbor. */
inline	const struct  reiserfs_key * get_rkey  (
	                const struct path         * p_s_chk_path,
                        const struct super_block  * p_s_sb
                      ) {
  int                   n_position,
    			n_path_offset = p_s_chk_path->path_length;
  struct buffer_head  * p_s_parent;

  RFALSE( n_path_offset < FIRST_PATH_ELEMENT_OFFSET,
	  "PAP-5030: invalid offset in the path");

  while ( n_path_offset-- > FIRST_PATH_ELEMENT_OFFSET ) {

    RFALSE( ! buffer_uptodate(PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset)),
	    "PAP-5040: parent is not uptodate");

    /* Parent at the path is not in the tree now. */
    if ( ! B_IS_IN_TREE(p_s_parent = PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset)) )
      return &MIN_KEY;
    /* Check whether position in the parent is correct. */
    if ( (n_position = PATH_OFFSET_POSITION(p_s_chk_path, n_path_offset)) > B_NR_ITEMS(p_s_parent) )
      return &MIN_KEY;
    /* Check whether parent at the path really points to the child. */
    if ( B_N_CHILD_NUM(p_s_parent, n_position) !=
                                        PATH_OFFSET_PBUFFER(p_s_chk_path, n_path_offset + 1)->b_blocknr )
      return &MIN_KEY;
    /* Return delimiting key if position in the parent is not the last one. */
    if ( n_position != B_NR_ITEMS(p_s_parent) )
      return B_N_PDELIM_KEY(p_s_parent, n_position);
  }
  /* Return MAX_KEY if we are in the root of the buffer tree. */
  if ( PATH_OFFSET_PBUFFER(p_s_chk_path, FIRST_PATH_ELEMENT_OFFSET)->b_blocknr ==
       SB_ROOT_BLOCK (p_s_sb) )
    return &MAX_KEY;
  return  &MIN_KEY;
}


/* Check whether a key is contained in the tree rooted from a buffer at a path. */
/* This works by looking at the left and right delimiting keys for the buffer in the last path_element in
   the path.  These delimiting keys are stored at least one level above that buffer in the tree. If the
   buffer is the first or last node in the tree order then one of the delimiting keys may be absent, and in
   this case get_lkey and get_rkey return a special key which is MIN_KEY or MAX_KEY. */
static  inline  int key_in_buffer (
                      struct path         * p_s_chk_path, /* Path which should be checked.  */
                      const struct cpu_key      * p_s_key,      /* Key which should be checked.   */
                      struct super_block  * p_s_sb        /* Super block pointer.           */
		      ) {

  RFALSE( ! p_s_key || p_s_chk_path->path_length < FIRST_PATH_ELEMENT_OFFSET ||
	  p_s_chk_path->path_length > MAX_HEIGHT,
	  "PAP-5050: pointer to the key(%p) is NULL or invalid path length(%d)",
	  p_s_key, p_s_chk_path->path_length);
  RFALSE( !PATH_PLAST_BUFFER(p_s_chk_path)->b_bdev,
	  "PAP-5060: device must not be NODEV");

  if ( comp_keys(get_lkey(p_s_chk_path, p_s_sb), p_s_key) == 1 )
    /* left delimiting key is bigger, that the key we look for */
    return 0;
  //  if ( comp_keys(p_s_key, get_rkey(p_s_chk_path, p_s_sb)) != -1 )
  if ( comp_keys(get_rkey(p_s_chk_path, p_s_sb), p_s_key) != 1 )
    /* p_s_key must be less than right delimitiing key */
    return 0;
  return 1;
}


inline void decrement_bcount(
              struct buffer_head  * p_s_bh
            ) { 
  if ( p_s_bh ) {
    if ( atomic_read (&(p_s_bh->b_count)) ) {
      put_bh(p_s_bh) ;
      return;
    }
    reiserfs_panic(NULL, "PAP-5070: decrement_bcount: trying to free free buffer %b", p_s_bh);
  }
}


/* Decrement b_count field of the all buffers in the path. */
void decrement_counters_in_path (
              struct path * p_s_search_path
            ) {
  int n_path_offset = p_s_search_path->path_length;

  RFALSE( n_path_offset < ILLEGAL_PATH_ELEMENT_OFFSET ||
	  n_path_offset > EXTENDED_MAX_HEIGHT - 1,
	  "PAP-5080: invalid path offset of %d", n_path_offset);

  while ( n_path_offset > ILLEGAL_PATH_ELEMENT_OFFSET ) {
    struct buffer_head * bh;

    bh = PATH_OFFSET_PBUFFER(p_s_search_path, n_path_offset--);
    decrement_bcount (bh);
  }
  p_s_search_path->path_length = ILLEGAL_PATH_ELEMENT_OFFSET;
}


int reiserfs_check_path(struct path *p) {
  RFALSE( p->path_length != ILLEGAL_PATH_ELEMENT_OFFSET,
	  "path not properly relsed") ;
  return 0 ;
}


/* Release all buffers in the path. Restore dirty bits clean
** when preparing the buffer for the log
**
** only called from fix_nodes()
*/
void  pathrelse_and_restore (
	struct super_block *s, 
        struct path * p_s_search_path
      ) {
  int n_path_offset = p_s_search_path->path_length;

  RFALSE( n_path_offset < ILLEGAL_PATH_ELEMENT_OFFSET, 
	  "clm-4000: invalid path offset");
  
  while ( n_path_offset > ILLEGAL_PATH_ELEMENT_OFFSET )  {
    reiserfs_restore_prepared_buffer(s, PATH_OFFSET_PBUFFER(p_s_search_path, 
                                     n_path_offset));
    brelse(PATH_OFFSET_PBUFFER(p_s_search_path, n_path_offset--));
  }
  p_s_search_path->path_length = ILLEGAL_PATH_ELEMENT_OFFSET;
}

/* Release all buffers in the path. */
void  pathrelse (
        struct path * p_s_search_path
      ) {
  int n_path_offset = p_s_search_path->path_length;

  RFALSE( n_path_offset < ILLEGAL_PATH_ELEMENT_OFFSET,
	  "PAP-5090: invalid path offset");
  
  while ( n_path_offset > ILLEGAL_PATH_ELEMENT_OFFSET )  
    brelse(PATH_OFFSET_PBUFFER(p_s_search_path, n_path_offset--));

  p_s_search_path->path_length = ILLEGAL_PATH_ELEMENT_OFFSET;
}



static int is_leaf (char * buf, int blocksize, struct buffer_head * bh)
{
    struct block_head * blkh;
    struct item_head * ih;
    int used_space;
    int prev_location;
    int i;
    int nr;

    blkh = (struct block_head *)buf;
    if ( blkh_level(blkh) != DISK_LEAF_NODE_LEVEL) {
	reiserfs_warning (NULL, "is_leaf: this should be caught earlier");
	return 0;
    }

    nr = blkh_nr_item(blkh);
    if (nr < 1 || nr > ((blocksize - BLKH_SIZE) / (IH_SIZE + MIN_ITEM_LEN))) {
	/* item number is too big or too small */
	reiserfs_warning (NULL, "is_leaf: nr_item seems wrong: %z", bh);
	return 0;
    }
    ih = (struct item_head *)(buf + BLKH_SIZE) + nr - 1;
    used_space = BLKH_SIZE + IH_SIZE * nr + (blocksize - ih_location (ih));
    if (used_space != blocksize - blkh_free_space(blkh)) {
	/* free space does not match to calculated amount of use space */
	reiserfs_warning (NULL, "is_leaf: free space seems wrong: %z", bh);
	return 0;
    }

    // FIXME: it is_leaf will hit performance too much - we may have
    // return 1 here

    /* check tables of item heads */
    ih = (struct item_head *)(buf + BLKH_SIZE);
    prev_location = blocksize;
    for (i = 0; i < nr; i ++, ih ++) {
	if ( le_ih_k_type(ih) == TYPE_ANY) {
	    reiserfs_warning (NULL, "is_leaf: wrong item type for item %h",ih);
	    return 0;
	}
	if (ih_location (ih) >= blocksize || ih_location (ih) < IH_SIZE * nr) {
	    reiserfs_warning (NULL, "is_leaf: item location seems wrong: %h", ih);
	    return 0;
	}
	if (ih_item_len (ih) < 1 || ih_item_len (ih) > MAX_ITEM_LEN (blocksize)) {
	    reiserfs_warning (NULL, "is_leaf: item length seems wrong: %h", ih);
	    return 0;
	}
	if (prev_location - ih_location (ih) != ih_item_len (ih)) {
	    reiserfs_warning (NULL, "is_leaf: item location seems wrong (second one): %h", ih);
	    return 0;
	}
	prev_location = ih_location (ih);
    }

    // one may imagine much more checks
    return 1;
}


/* returns 1 if buf looks like an internal node, 0 otherwise */
static int is_internal (char * buf, int blocksize, struct buffer_head * bh)
{
    struct block_head * blkh;
    int nr;
    int used_space;

    blkh = (struct block_head *)buf;
    nr = blkh_level(blkh);
    if (nr <= DISK_LEAF_NODE_LEVEL || nr > MAX_HEIGHT) {
	/* this level is not possible for internal nodes */
	reiserfs_warning (NULL, "is_internal: this should be caught earlier");
	return 0;
    }
    
    nr = blkh_nr_item(blkh);
    if (nr > (blocksize - BLKH_SIZE - DC_SIZE) / (KEY_SIZE + DC_SIZE)) {
	/* for internal which is not root we might check min number of keys */
	reiserfs_warning (NULL, "is_internal: number of key seems wrong: %z", bh);
	return 0;
    }

    used_space = BLKH_SIZE + KEY_SIZE * nr + DC_SIZE * (nr + 1);
    if (used_space != blocksize - blkh_free_space(blkh)) {
	reiserfs_warning (NULL, "is_internal: free space seems wrong: %z", bh);
	return 0;
    }

    // one may imagine much more checks
    return 1;
}


// make sure that bh contains formatted node of reiserfs tree of
// 'level'-th level
static int is_tree_node (struct buffer_head * bh, int level)
{
    if (B_LEVEL (bh) != level) {
	reiserfs_warning (NULL, "is_tree_node: node level %d does not match to the expected one %d",
		B_LEVEL (bh), level);
	return 0;
    }
    if (level == DISK_LEAF_NODE_LEVEL)
	return is_leaf (bh->b_data, bh->b_size, bh);

    return is_internal (bh->b_data, bh->b_size, bh);
}



#define SEARCH_BY_KEY_READA 16

/* The function is NOT SCHEDULE-SAFE! */
static void search_by_key_reada (struct super_block * s,
                                 struct buffer_head **bh,
				 unsigned long *b, int num)
{
    int i,j;
  
    for (i = 0 ; i < num ; i++) {
	bh[i] = sb_getblk (s, b[i]);
    }
    for (j = 0 ; j < i ; j++) {
	/*
	 * note, this needs attention if we are getting rid of the BKL
	 * you have to make sure the prepared bit isn't set on this buffer
	 */
	if (!buffer_uptodate(bh[j]))
	    ll_rw_block(READA, 1, bh + j);
    	brelse(bh[j]);
    }
}

/**************************************************************************
 * Algorithm   SearchByKey                                                *
 *             look for item in the Disk S+Tree by its key                *
 * Input:  p_s_sb   -  super block                                        *
 *         p_s_key  - pointer to the key to search                        *
 * Output: ITEM_FOUND, ITEM_NOT_FOUND or IO_ERROR                         *
 *         p_s_search_path - path from the root to the needed leaf        *
 **************************************************************************/

/* This function fills up the path from the root to the leaf as it
   descends the tree looking for the key.  It uses reiserfs_bread to
   try to find buffers in the cache given their block number.  If it
   does not find them in the cache it reads them from disk.  For each
   node search_by_key finds using reiserfs_bread it then uses
   bin_search to look through that node.  bin_search will find the
   position of the block_number of the next node if it is looking
   through an internal node.  If it is looking through a leaf node
   bin_search will find the position of the item which has key either
   equal to given key, or which is the maximal key less than the given
   key.  search_by_key returns a path that must be checked for the
   correctness of the top of the path but need not be checked for the
   correctness of the bottom of the path */
/* The function is NOT SCHEDULE-SAFE! */
int search_by_key (struct super_block * p_s_sb,
		   const struct cpu_key * p_s_key, /* Key to search. */
		   struct path * p_s_search_path, /* This structure was
						     allocated and initialized
						     by the calling
						     function. It is filled up
						     by this function.  */
		   int n_stop_level /* How far down the tree to search. To
                                       stop at leaf level - set to
                                       DISK_LEAF_NODE_LEVEL */
    ) {
    int  n_block_number;
    int  expected_level;
    struct buffer_head  *       p_s_bh;
    struct path_element *       p_s_last_element;
    int				n_node_level, n_retval;
    int 			right_neighbor_of_leaf_node;
    int				fs_gen;
    struct buffer_head *reada_bh[SEARCH_BY_KEY_READA];
    unsigned long      reada_blocks[SEARCH_BY_KEY_READA];
    int reada_count = 0;

#ifdef CONFIG_REISERFS_CHECK
    int n_repeat_counter = 0;
#endif
    
    PROC_INFO_INC( p_s_sb, search_by_key );
    
    /* As we add each node to a path we increase its count.  This means that
       we must be careful to release all nodes in a path before we either
       discard the path struct or re-use the path struct, as we do here. */

    decrement_counters_in_path(p_s_search_path);

    right_neighbor_of_leaf_node = 0;

    /* With each iteration of this loop we search through the items in the
       current node, and calculate the next current node(next path element)
       for the next iteration of this loop.. */
    n_block_number = SB_ROOT_BLOCK (p_s_sb);
    expected_level = -1;
    while ( 1 ) {

#ifdef CONFIG_REISERFS_CHECK
	if ( !(++n_repeat_counter % 50000) )
	    reiserfs_warning (p_s_sb, "PAP-5100: search_by_key: %s:"
			      "there were %d iterations of while loop "
			      "looking for key %K",
			      current->comm, n_repeat_counter, p_s_key);
#endif

	/* prep path to have another element added to it. */
	p_s_last_element = PATH_OFFSET_PELEMENT(p_s_search_path, ++p_s_search_path->path_length);
	fs_gen = get_generation (p_s_sb);

	/* Read the next tree node, and set the last element in the path to
           have a pointer to it. */
	if ((p_s_bh = p_s_last_element->pe_buffer =
	     sb_getblk(p_s_sb, n_block_number)) ) {
	    if (!buffer_uptodate(p_s_bh) && reada_count > 1) {
		search_by_key_reada (p_s_sb, reada_bh,
		                     reada_blocks, reada_count);
	    }
	    ll_rw_block(READ, 1, &p_s_bh);
	    wait_on_buffer(p_s_bh);
	    if (!buffer_uptodate(p_s_bh))
	        goto io_error;
	} else {
io_error:
	    p_s_search_path->path_length --;
	    pathrelse(p_s_search_path);
	    return IO_ERROR;
	}
	reada_count = 0;
	if (expected_level == -1)
		expected_level = SB_TREE_HEIGHT (p_s_sb);
	expected_level --;

	/* It is possible that schedule occurred. We must check whether the key
	   to search is still in the tree rooted from the current buffer. If
	   not then repeat search from the root. */
	if ( fs_changed (fs_gen, p_s_sb) && 
	    (!B_IS_IN_TREE (p_s_bh) ||
	     B_LEVEL(p_s_bh) != expected_level ||
	     !key_in_buffer(p_s_search_path, p_s_key, p_s_sb))) {
	    PROC_INFO_INC( p_s_sb, search_by_key_fs_changed );
	    PROC_INFO_INC( p_s_sb, search_by_key_restarted );
	    PROC_INFO_INC( p_s_sb, sbk_restarted[ expected_level - 1 ] );
	    decrement_counters_in_path(p_s_search_path);
	    
	    /* Get the root block number so that we can repeat the search
	       starting from the root. */
	    n_block_number = SB_ROOT_BLOCK (p_s_sb);
	    expected_level = -1;
	    right_neighbor_of_leaf_node = 0;
	    
	    /* repeat search from the root */
	    continue;
	}

        /* only check that the key is in the buffer if p_s_key is not
           equal to the MAX_KEY. Latter case is only possible in
           "finish_unfinished()" processing during mount. */
        RFALSE( comp_keys( &MAX_KEY, p_s_key ) &&
                ! key_in_buffer(p_s_search_path, p_s_key, p_s_sb),
		"PAP-5130: key is not in the buffer");
#ifdef CONFIG_REISERFS_CHECK
	if ( cur_tb ) {
	    print_cur_tb ("5140");
	    reiserfs_panic(p_s_sb, "PAP-5140: search_by_key: schedule occurred in do_balance!");
	}
#endif

	// make sure, that the node contents look like a node of
	// certain level
	if (!is_tree_node (p_s_bh, expected_level)) {
	    reiserfs_warning (p_s_sb, "vs-5150: search_by_key: "
			      "invalid format found in block %ld. Fsck?",
			      p_s_bh->b_blocknr);
	    pathrelse (p_s_search_path);
	    return IO_ERROR;
	}
	
	/* ok, we have acquired next formatted node in the tree */
	n_node_level = B_LEVEL (p_s_bh);

	PROC_INFO_BH_STAT( p_s_sb, p_s_bh, n_node_level - 1 );

	RFALSE( n_node_level < n_stop_level,
		"vs-5152: tree level (%d) is less than stop level (%d)",
		n_node_level, n_stop_level);

	n_retval = bin_search( p_s_key, B_N_PITEM_HEAD(p_s_bh, 0),
                B_NR_ITEMS(p_s_bh),
                ( n_node_level == DISK_LEAF_NODE_LEVEL ) ? IH_SIZE : KEY_SIZE,
                &(p_s_last_element->pe_position));
	if (n_node_level == n_stop_level) {
	    return n_retval;
	}

	/* we are not in the stop level */
	if (n_retval == ITEM_FOUND)
	    /* item has been found, so we choose the pointer which is to the right of the found one */
	    p_s_last_element->pe_position++;

	/* if item was not found we choose the position which is to
	   the left of the found item. This requires no code,
	   bin_search did it already.*/

	/* So we have chosen a position in the current node which is
	   an internal node.  Now we calculate child block number by
	   position in the node. */
	n_block_number = B_N_CHILD_NUM(p_s_bh, p_s_last_element->pe_position);

	/* if we are going to read leaf nodes, try for read ahead as well */
	if ((p_s_search_path->reada & PATH_READA) &&
	    n_node_level == DISK_LEAF_NODE_LEVEL + 1)
	{
	    int pos = p_s_last_element->pe_position;
	    int limit = B_NR_ITEMS(p_s_bh);
	    struct reiserfs_key *le_key;

	    if (p_s_search_path->reada & PATH_READA_BACK)
		limit = 0;
	    while(reada_count < SEARCH_BY_KEY_READA) {
		if (pos == limit)
		    break;
	        reada_blocks[reada_count++] = B_N_CHILD_NUM(p_s_bh, pos);
		if (p_s_search_path->reada & PATH_READA_BACK)
		    pos--;
		else
		    pos++;

		/*
		 * check to make sure we're in the same object
		 */
		le_key = B_N_PDELIM_KEY(p_s_bh, pos);
		if (le32_to_cpu(le_key->k_objectid) !=
		    p_s_key->on_disk_key.k_objectid)
		{
		    break;
		}
	    }
        }
    }
}


/* Form the path to an item and position in this item which contains
   file byte defined by p_s_key. If there is no such item
   corresponding to the key, we point the path to the item with
   maximal key less than p_s_key, and *p_n_pos_in_item is set to one
   past the last entry/byte in the item.  If searching for entry in a
   directory item, and it is not found, *p_n_pos_in_item is set to one
   entry more than the entry with maximal key which is less than the
   sought key.

   Note that if there is no entry in this same node which is one more,
   then we point to an imaginary entry.  for direct items, the
   position is in units of bytes, for indirect items the position is
   in units of blocknr entries, for directory items the position is in
   units of directory entries.  */

/* The function is NOT SCHEDULE-SAFE! */
int search_for_position_by_key (struct super_block  * p_s_sb,         /* Pointer to the super block.          */
				const struct cpu_key  * p_cpu_key,      /* Key to search (cpu variable)         */
				struct path         * p_s_search_path /* Filled up by this function.          */
    ) {
    struct item_head    * p_le_ih; /* pointer to on-disk structure */
    int                   n_blk_size;
    loff_t item_offset, offset;
    struct reiserfs_dir_entry de;
    int retval;

    /* If searching for directory entry. */
    if ( is_direntry_cpu_key (p_cpu_key) )
	return  search_by_entry_key (p_s_sb, p_cpu_key, p_s_search_path, &de);

    /* If not searching for directory entry. */
    
    /* If item is found. */
    retval = search_item (p_s_sb, p_cpu_key, p_s_search_path);
    if (retval == IO_ERROR)
	return retval;
    if ( retval == ITEM_FOUND )  {

	RFALSE( ! ih_item_len(
                B_N_PITEM_HEAD(PATH_PLAST_BUFFER(p_s_search_path),
			       PATH_LAST_POSITION(p_s_search_path))),
	        "PAP-5165: item length equals zero");

	pos_in_item(p_s_search_path) = 0;
	return POSITION_FOUND;
    }

    RFALSE( ! PATH_LAST_POSITION(p_s_search_path),
	    "PAP-5170: position equals zero");

    /* Item is not found. Set path to the previous item. */
    p_le_ih = B_N_PITEM_HEAD(PATH_PLAST_BUFFER(p_s_search_path), --PATH_LAST_POSITION(p_s_search_path));
    n_blk_size = p_s_sb->s_blocksize;

    if (comp_short_keys (&(p_le_ih->ih_key), p_cpu_key)) {
	return FILE_NOT_FOUND;
    }

    // FIXME: quite ugly this far

    item_offset = le_ih_k_offset (p_le_ih);
    offset = cpu_key_k_offset (p_cpu_key);

    /* Needed byte is contained in the item pointed to by the path.*/
    if (item_offset <= offset &&
	item_offset + op_bytes_number (p_le_ih, n_blk_size) > offset) {
	pos_in_item (p_s_search_path) = offset - item_offset;
	if ( is_indirect_le_ih(p_le_ih) ) {
	    pos_in_item (p_s_search_path) /= n_blk_size;
	}
	return POSITION_FOUND;
    }

    /* Needed byte is not contained in the item pointed to by the
     path. Set pos_in_item out of the item. */
    if ( is_indirect_le_ih (p_le_ih) )
	pos_in_item (p_s_search_path) = ih_item_len(p_le_ih) / UNFM_P_SIZE;
    else
        pos_in_item (p_s_search_path) = ih_item_len( p_le_ih );
  
    return POSITION_NOT_FOUND;
}


/* Compare given item and item pointed to by the path. */
int comp_items (const struct item_head * stored_ih, const struct path * p_s_path)
{
    struct buffer_head  * p_s_bh;
    struct item_head    * ih;

    /* Last buffer at the path is not in the tree. */
    if ( ! B_IS_IN_TREE(p_s_bh = PATH_PLAST_BUFFER(p_s_path)) )
	return 1;

    /* Last path position is invalid. */
    if ( PATH_LAST_POSITION(p_s_path) >= B_NR_ITEMS(p_s_bh) )
	return 1;

    /* we need only to know, whether it is the same item */
    ih = get_ih (p_s_path);
    return memcmp (stored_ih, ih, IH_SIZE);
}


/* unformatted nodes are not logged anymore, ever.  This is safe
** now
*/
#define held_by_others(bh) (atomic_read(&(bh)->b_count) > 1)

// block can not be forgotten as it is in I/O or held by someone
#define block_in_use(bh) (buffer_locked(bh) || (held_by_others(bh)))



// prepare for delete or cut of direct item
static inline int prepare_for_direct_item (struct path * path,
					   struct item_head * le_ih,
					   struct inode * inode,
					   loff_t new_file_length,
					   int * cut_size)
{
    loff_t round_len;


    if ( new_file_length == max_reiserfs_offset (inode) ) {
	/* item has to be deleted */
	*cut_size = -(IH_SIZE + ih_item_len(le_ih));
	return M_DELETE;
    }
	
    // new file gets truncated
    if (get_inode_item_key_version (inode) == KEY_FORMAT_3_6) {
	// 
	round_len = ROUND_UP (new_file_length); 
	/* this was n_new_file_length < le_ih ... */
	if ( round_len < le_ih_k_offset (le_ih) )  {
	    *cut_size = -(IH_SIZE + ih_item_len(le_ih));
	    return M_DELETE; /* Delete this item. */
	}
	/* Calculate first position and size for cutting from item. */
	pos_in_item (path) = round_len - (le_ih_k_offset (le_ih) - 1);
	*cut_size = -(ih_item_len(le_ih) - pos_in_item(path));
	
	return M_CUT; /* Cut from this item. */
    }


    // old file: items may have any length

    if ( new_file_length < le_ih_k_offset (le_ih) )  {
	*cut_size = -(IH_SIZE + ih_item_len(le_ih));
	return M_DELETE; /* Delete this item. */
    }
    /* Calculate first position and size for cutting from item. */
    *cut_size = -(ih_item_len(le_ih) -
		      (pos_in_item (path) = new_file_length + 1 - le_ih_k_offset (le_ih)));
    return M_CUT; /* Cut from this item. */
}


static inline int prepare_for_direntry_item (struct path * path,
					     struct item_head * le_ih,
					     struct inode * inode,
					     loff_t new_file_length,
					     int * cut_size)
{
    if (le_ih_k_offset (le_ih) == DOT_OFFSET && 
	new_file_length == max_reiserfs_offset (inode)) {
	RFALSE( ih_entry_count (le_ih) != 2,
	        "PAP-5220: incorrect empty directory item (%h)", le_ih);
	*cut_size = -(IH_SIZE + ih_item_len(le_ih));
	return M_DELETE; /* Delete the directory item containing "." and ".." entry. */
    }
    
    if ( ih_entry_count (le_ih) == 1 )  {
	/* Delete the directory item such as there is one record only
	   in this item*/
	*cut_size = -(IH_SIZE + ih_item_len(le_ih));
	return M_DELETE;
    }
    
    /* Cut one record from the directory item. */
    *cut_size = -(DEH_SIZE + entry_length (get_last_bh (path), le_ih, pos_in_item (path)));
    return M_CUT; 
}


/*  If the path points to a directory or direct item, calculate mode and the size cut, for balance.
    If the path points to an indirect item, remove some number of its unformatted nodes.
    In case of file truncate calculate whether this item must be deleted/truncated or last
    unformatted node of this item will be converted to a direct item.
    This function returns a determination of what balance mode the calling function should employ. */
static char  prepare_for_delete_or_cut(
				       struct reiserfs_transaction_handle *th, 
				       struct inode * inode,
				       struct path         * p_s_path,
				       const struct cpu_key      * p_s_item_key,
				       int                 * p_n_removed,      /* Number of unformatted nodes which were removed
										  from end of the file. */
				       int                 * p_n_cut_size,
				       unsigned long long    n_new_file_length /* MAX_KEY_OFFSET in case of delete. */
    ) {
    struct super_block  * p_s_sb = inode->i_sb;
    struct item_head    * p_le_ih = PATH_PITEM_HEAD(p_s_path);
    struct buffer_head  * p_s_bh = PATH_PLAST_BUFFER(p_s_path);

    BUG_ON (!th->t_trans_id);

    /* Stat_data item. */
    if ( is_statdata_le_ih (p_le_ih) ) {

	RFALSE( n_new_file_length != max_reiserfs_offset (inode),
		"PAP-5210: mode must be M_DELETE");

	*p_n_cut_size = -(IH_SIZE + ih_item_len(p_le_ih));
	return M_DELETE;
    }


    /* Directory item. */
    if ( is_direntry_le_ih (p_le_ih) )
	return prepare_for_direntry_item (p_s_path, p_le_ih, inode, n_new_file_length, p_n_cut_size);

    /* Direct item. */
    if ( is_direct_le_ih (p_le_ih) )
	return prepare_for_direct_item (p_s_path, p_le_ih, inode, n_new_file_length, p_n_cut_size);


    /* Case of an indirect item. */
    {
	int                   n_unfm_number,    /* Number of the item unformatted nodes. */
	    n_counter,
	    n_blk_size;
	__le32               * p_n_unfm_pointer; /* Pointer to the unformatted node number. */
	__u32 tmp;
	struct item_head      s_ih;           /* Item header. */
	char                  c_mode;           /* Returned mode of the balance. */
	int need_research;


	n_blk_size = p_s_sb->s_blocksize;

	/* Search for the needed object indirect item until there are no unformatted nodes to be removed. */
	do  {
	    need_research = 0;
            p_s_bh = PATH_PLAST_BUFFER(p_s_path);
	    /* Copy indirect item header to a temp variable. */
	    copy_item_head(&s_ih, PATH_PITEM_HEAD(p_s_path));
	    /* Calculate number of unformatted nodes in this item. */
	    n_unfm_number = I_UNFM_NUM(&s_ih);

	    RFALSE( ! is_indirect_le_ih(&s_ih) || ! n_unfm_number ||
		    pos_in_item (p_s_path) + 1 !=  n_unfm_number,
		    "PAP-5240: invalid item %h "
		    "n_unfm_number = %d *p_n_pos_in_item = %d", 
		    &s_ih, n_unfm_number, pos_in_item (p_s_path));

	    /* Calculate balance mode and position in the item to remove unformatted nodes. */
	    if ( n_new_file_length == max_reiserfs_offset (inode) ) {/* Case of delete. */
		pos_in_item (p_s_path) = 0;
		*p_n_cut_size = -(IH_SIZE + ih_item_len(&s_ih));
		c_mode = M_DELETE;
	    }
	    else  { /* Case of truncate. */
		if ( n_new_file_length < le_ih_k_offset (&s_ih) )  {
		    pos_in_item (p_s_path) = 0;
		    *p_n_cut_size = -(IH_SIZE + ih_item_len(&s_ih));
		    c_mode = M_DELETE; /* Delete this item. */
		}
		else  {
		    /* indirect item must be truncated starting from *p_n_pos_in_item-th position */
		    pos_in_item (p_s_path) = (n_new_file_length + n_blk_size - le_ih_k_offset (&s_ih) ) >> p_s_sb->s_blocksize_bits;

		    RFALSE( pos_in_item (p_s_path) > n_unfm_number,
			    "PAP-5250: invalid position in the item");

		    /* Either convert last unformatted node of indirect item to direct item or increase
		       its free space.  */
		    if ( pos_in_item (p_s_path) == n_unfm_number )  {
			*p_n_cut_size = 0; /* Nothing to cut. */
			return M_CONVERT; /* Maybe convert last unformatted node to the direct item. */
		    }
		    /* Calculate size to cut. */
		    *p_n_cut_size = -(ih_item_len(&s_ih) - pos_in_item(p_s_path) * UNFM_P_SIZE);

		    c_mode = M_CUT;     /* Cut from this indirect item. */
		}
	    }

	    RFALSE( n_unfm_number <= pos_in_item (p_s_path),
		    "PAP-5260: invalid position in the indirect item");

	    /* pointers to be cut */
	    n_unfm_number -= pos_in_item (p_s_path);
	    /* Set pointer to the last unformatted node pointer that is to be cut. */
	    p_n_unfm_pointer = (__le32 *)B_I_PITEM(p_s_bh, &s_ih) + I_UNFM_NUM(&s_ih) - 1 - *p_n_removed;


	    /* We go through the unformatted nodes pointers of the indirect
	       item and look for the unformatted nodes in the cache. If we
	       found some of them we free it, zero corresponding indirect item
	       entry and log buffer containing that indirect item. For this we
	       need to prepare last path element for logging. If some
	       unformatted node has b_count > 1 we must not free this
	       unformatted node since it is in use. */
	    reiserfs_prepare_for_journal(p_s_sb, p_s_bh, 1);
	    // note: path could be changed, first line in for loop takes care
	    // of it

	    for (n_counter = *p_n_removed;
		 n_counter < n_unfm_number; n_counter++, p_n_unfm_pointer-- ) {

		cond_resched();
		if (item_moved (&s_ih, p_s_path)) {
		    need_research = 1 ;
		    break;
		}
		RFALSE( p_n_unfm_pointer < (__le32 *)B_I_PITEM(p_s_bh, &s_ih) ||
			p_n_unfm_pointer > (__le32 *)B_I_PITEM(p_s_bh, &s_ih) + I_UNFM_NUM(&s_ih) - 1,
			"vs-5265: pointer out of range");

		/* Hole, nothing to remove. */
		if ( ! get_block_num(p_n_unfm_pointer,0) )  {
			(*p_n_removed)++;
			continue;
		}

		(*p_n_removed)++;

		tmp = get_block_num(p_n_unfm_pointer,0);
		put_block_num(p_n_unfm_pointer, 0, 0);
		journal_mark_dirty (th, p_s_sb, p_s_bh);
		reiserfs_free_block(th, inode, tmp, 1);
		if ( item_moved (&s_ih, p_s_path) )  {
			need_research = 1;
			break ;
		}
	    }

	    /* a trick.  If the buffer has been logged, this
	    ** will do nothing.  If we've broken the loop without
	    ** logging it, it will restore the buffer
	    **
	    */
	    reiserfs_restore_prepared_buffer(p_s_sb, p_s_bh);

	    /* This loop can be optimized. */
	} while ( (*p_n_removed < n_unfm_number || need_research) &&
		  search_for_position_by_key(p_s_sb, p_s_item_key, p_s_path) == POSITION_FOUND );

	RFALSE( *p_n_removed < n_unfm_number, 
		"PAP-5310: indirect item is not found");
	RFALSE( item_moved (&s_ih, p_s_path), 
		"after while, comp failed, retry") ;

	if (c_mode == M_CUT)
	    pos_in_item (p_s_path) *= UNFM_P_SIZE;
	return c_mode;
    }
}

/* Calculate number of bytes which will be deleted or cut during balance */
static int calc_deleted_bytes_number(
    struct  tree_balance  * p_s_tb,
    char                    c_mode
    ) {
    int                     n_del_size;
    struct  item_head     * p_le_ih = PATH_PITEM_HEAD(p_s_tb->tb_path);

    if ( is_statdata_le_ih (p_le_ih) )
	return 0;

    n_del_size = ( c_mode == M_DELETE ) ? ih_item_len(p_le_ih) : -p_s_tb->insert_size[0];
    if ( is_direntry_le_ih (p_le_ih) ) {
	// return EMPTY_DIR_SIZE; /* We delete emty directoris only. */
	// we can't use EMPTY_DIR_SIZE, as old format dirs have a different
	// empty size.  ick. FIXME, is this right?
	//
	return n_del_size ;
    }

    if ( is_indirect_le_ih (p_le_ih) )
	n_del_size = (n_del_size/UNFM_P_SIZE)*
	  (PATH_PLAST_BUFFER(p_s_tb->tb_path)->b_size);// - get_ih_free_space (p_le_ih);
    return n_del_size;
}

static void init_tb_struct(
    struct reiserfs_transaction_handle *th,
    struct tree_balance * p_s_tb,
    struct super_block  * p_s_sb,
    struct path         * p_s_path,
    int                   n_size
    ) {

    BUG_ON (!th->t_trans_id);

    memset (p_s_tb,'\0',sizeof(struct tree_balance));
    p_s_tb->transaction_handle = th ;
    p_s_tb->tb_sb = p_s_sb;
    p_s_tb->tb_path = p_s_path;
    PATH_OFFSET_PBUFFER(p_s_path, ILLEGAL_PATH_ELEMENT_OFFSET) = NULL;
    PATH_OFFSET_POSITION(p_s_path, ILLEGAL_PATH_ELEMENT_OFFSET) = 0;
    p_s_tb->insert_size[0] = n_size;
}



void padd_item (char * item, int total_length, int length)
{
    int i;

    for (i = total_length; i > length; )
	item [--i] = 0;
}

#ifdef REISERQUOTA_DEBUG
char key2type(struct reiserfs_key *ih)
{
  if (is_direntry_le_key(2, ih))
    return 'd';
  if (is_direct_le_key(2, ih))
    return 'D';
  if (is_indirect_le_key(2, ih))
    return 'i';
  if (is_statdata_le_key(2, ih))
    return 's';
  return 'u';
}

char head2type(struct item_head *ih)
{
  if (is_direntry_le_ih(ih))
    return 'd';
  if (is_direct_le_ih(ih))
    return 'D';
  if (is_indirect_le_ih(ih))
    return 'i';
  if (is_statdata_le_ih(ih))
    return 's';
  return 'u';
}
#endif

/* Delete object item. */
int reiserfs_delete_item (struct reiserfs_transaction_handle *th, 
			  struct path * p_s_path, /* Path to the deleted item. */
			  const struct cpu_key * p_s_item_key, /* Key to search for the deleted item.  */
			  struct inode * p_s_inode,/* inode is here just to update i_blocks and quotas */
			  struct buffer_head  * p_s_un_bh)    /* NULL or unformatted node pointer.    */
{
    struct super_block * p_s_sb = p_s_inode->i_sb;
    struct tree_balance   s_del_balance;
    struct item_head      s_ih;
    struct item_head      *q_ih;
    int			  quota_cut_bytes;
    int                   n_ret_value,
	n_del_size,
	n_removed;

#ifdef CONFIG_REISERFS_CHECK
    char                  c_mode;
    int			n_iter = 0;
#endif

    BUG_ON (!th->t_trans_id);

    init_tb_struct(th, &s_del_balance, p_s_sb, p_s_path, 0/*size is unknown*/);

    while ( 1 ) {
	n_removed = 0;

#ifdef CONFIG_REISERFS_CHECK
	n_iter++;
	c_mode =
#endif
	    prepare_for_delete_or_cut(th, p_s_inode, p_s_path, p_s_item_key, &n_removed, &n_del_size, max_reiserfs_offset (p_s_inode));

	RFALSE( c_mode != M_DELETE, "PAP-5320: mode must be M_DELETE");

	copy_item_head(&s_ih, PATH_PITEM_HEAD(p_s_path));
	s_del_balance.insert_size[0] = n_del_size;

	n_ret_value = fix_nodes(M_DELETE, &s_del_balance, NULL, NULL);
	if ( n_ret_value != REPEAT_SEARCH )
	    break;

	PROC_INFO_INC( p_s_sb, delete_item_restarted );

	// file system changed, repeat search
	n_ret_value = search_for_position_by_key(p_s_sb, p_s_item_key, p_s_path);
	if (n_ret_value == IO_ERROR)
	    break;
	if (n_ret_value == FILE_NOT_FOUND) {
	    reiserfs_warning (p_s_sb, "vs-5340: reiserfs_delete_item: "
			      "no items of the file %K found", p_s_item_key);
	    break;
	}
    } /* while (1) */

    if ( n_ret_value != CARRY_ON ) {
	unfix_nodes(&s_del_balance);
	return 0;
    }

    // reiserfs_delete_item returns item length when success
    n_ret_value = calc_deleted_bytes_number(&s_del_balance, M_DELETE);
    q_ih = get_ih(p_s_path) ;
    quota_cut_bytes = ih_item_len(q_ih) ;

    /* hack so the quota code doesn't have to guess if the file
    ** has a tail.  On tail insert, we allocate quota for 1 unformatted node.
    ** We test the offset because the tail might have been
    ** split into multiple items, and we only want to decrement for
    ** the unfm node once
    */
    if (!S_ISLNK (p_s_inode->i_mode) && is_direct_le_ih(q_ih)) {
        if ((le_ih_k_offset(q_ih) & (p_s_sb->s_blocksize - 1)) == 1) {
            quota_cut_bytes = p_s_sb->s_blocksize + UNFM_P_SIZE;
        } else {
	    quota_cut_bytes = 0 ;
	}
    }

    if ( p_s_un_bh )  {
	int off;
        char *data ;

	/* We are in direct2indirect conversion, so move tail contents
           to the unformatted node */
	/* note, we do the copy before preparing the buffer because we
	** don't care about the contents of the unformatted node yet.
	** the only thing we really care about is the direct item's data
	** is in the unformatted node.
	**
	** Otherwise, we would have to call reiserfs_prepare_for_journal on
	** the unformatted node, which might schedule, meaning we'd have to
	** loop all the way back up to the start of the while loop.
	**
	** The unformatted node must be dirtied later on.  We can't be
	** sure here if the entire tail has been deleted yet.
        **
        ** p_s_un_bh is from the page cache (all unformatted nodes are
        ** from the page cache) and might be a highmem page.  So, we
        ** can't use p_s_un_bh->b_data.
	** -clm
	*/

        data = kmap_atomic(p_s_un_bh->b_page, KM_USER0);
	off = ((le_ih_k_offset (&s_ih) - 1) & (PAGE_CACHE_SIZE - 1));
	memcpy(data + off,
	       B_I_PITEM(PATH_PLAST_BUFFER(p_s_path), &s_ih), n_ret_value);
	kunmap_atomic(data, KM_USER0);
    }
    /* Perform balancing after all resources have been collected at once. */ 
    do_balance(&s_del_balance, NULL, NULL, M_DELETE);

#ifdef REISERQUOTA_DEBUG
    reiserfs_debug (p_s_sb, REISERFS_DEBUG_CODE, "reiserquota delete_item(): freeing %u, id=%u type=%c", quota_cut_bytes, p_s_inode->i_uid, head2type(&s_ih));
#endif
    DQUOT_FREE_SPACE_NODIRTY(p_s_inode, quota_cut_bytes);

    /* Return deleted body length */
    return n_ret_value;
}


/* Summary Of Mechanisms For Handling Collisions Between Processes:

 deletion of the body of the object is performed by iput(), with the
 result that if multiple processes are operating on a file, the
 deletion of the body of the file is deferred until the last process
 that has an open inode performs its iput().

 writes and truncates are protected from collisions by use of
 semaphores.

 creates, linking, and mknod are protected from collisions with other
 processes by making the reiserfs_add_entry() the last step in the
 creation, and then rolling back all changes if there was a collision.
 - Hans
*/


/* this deletes item which never gets split */
void reiserfs_delete_solid_item (struct reiserfs_transaction_handle *th,
				 struct inode *inode,
				 struct reiserfs_key * key)
{
    struct tree_balance tb;
    INITIALIZE_PATH (path);
    int item_len = 0;
    int tb_init = 0 ;
    struct cpu_key cpu_key;
    int retval;
    int quota_cut_bytes = 0;

    BUG_ON (!th->t_trans_id);
    
    le_key2cpu_key (&cpu_key, key);
    
    while (1) {
	retval = search_item (th->t_super, &cpu_key, &path);
	if (retval == IO_ERROR) {
	    reiserfs_warning (th->t_super,
			      "vs-5350: reiserfs_delete_solid_item: "
			      "i/o failure occurred trying to delete %K",
			      &cpu_key);
	    break;
	}
	if (retval != ITEM_FOUND) {
	    pathrelse (&path);
	    // No need for a warning, if there is just no free space to insert '..' item into the newly-created subdir
	    if ( !( (unsigned long long) GET_HASH_VALUE (le_key_k_offset (le_key_version (key), key)) == 0 && \
		 (unsigned long long) GET_GENERATION_NUMBER (le_key_k_offset (le_key_version (key), key)) == 1 ) )
		reiserfs_warning (th->t_super, "vs-5355: reiserfs_delete_solid_item: %k not found", key);
	    break;
	}
	if (!tb_init) {
	    tb_init = 1 ;
	    item_len = ih_item_len( PATH_PITEM_HEAD(&path) );
	    init_tb_struct (th, &tb, th->t_super, &path, - (IH_SIZE + item_len));
	}
	quota_cut_bytes = ih_item_len(PATH_PITEM_HEAD(&path)) ;

	retval = fix_nodes (M_DELETE, &tb, NULL, NULL);
	if (retval == REPEAT_SEARCH) {
	    PROC_INFO_INC( th -> t_super, delete_solid_item_restarted );
	    continue;
	}

	if (retval == CARRY_ON) {
	    do_balance (&tb, NULL, NULL, M_DELETE);
	    if (inode) {	/* Should we count quota for item? (we don't count quotas for save-links) */
#ifdef REISERQUOTA_DEBUG
		reiserfs_debug (th->t_super, REISERFS_DEBUG_CODE, "reiserquota delete_solid_item(): freeing %u id=%u type=%c", quota_cut_bytes, inode->i_uid, key2type(key));
#endif
		DQUOT_FREE_SPACE_NODIRTY(inode, quota_cut_bytes);
	    }
	    break;
	}

	// IO_ERROR, NO_DISK_SPACE, etc
	reiserfs_warning (th->t_super, "vs-5360: reiserfs_delete_solid_item: "
			  "could not delete %K due to fix_nodes failure", &cpu_key);
	unfix_nodes (&tb);
	break;
    }

    reiserfs_check_path(&path) ;
}


int reiserfs_delete_object (struct reiserfs_transaction_handle *th, struct inode * inode)
{
    int err;
    inode->i_size = 0;
    BUG_ON (!th->t_trans_id);

    /* for directory this deletes item containing "." and ".." */
    err = reiserfs_do_truncate (th, inode, NULL, 0/*no timestamp updates*/);
    if (err)
        return err;
    
#if defined( USE_INODE_GENERATION_COUNTER )
    if( !old_format_only ( th -> t_super ) )
      {
       __le32 *inode_generation;
       
       inode_generation = 
         &REISERFS_SB(th -> t_super) -> s_rs -> s_inode_generation;
       *inode_generation = cpu_to_le32( le32_to_cpu( *inode_generation ) + 1 );
      }
/* USE_INODE_GENERATION_COUNTER */
#endif
    reiserfs_delete_solid_item (th, inode, INODE_PKEY (inode));

    return err;
}

static void
unmap_buffers(struct page *page, loff_t pos) {
    struct buffer_head *bh ;
    struct buffer_head *head ;
    struct buffer_head *next ;
    unsigned long tail_index ;
    unsigned long cur_index ;

    if (page) {
	if (page_has_buffers(page)) {
	    tail_index = pos & (PAGE_CACHE_SIZE - 1) ;
	    cur_index = 0 ;
	    head = page_buffers(page) ;
	    bh = head ;
	    do {
		next = bh->b_this_page ;

		/* we want to unmap the buffers that contain the tail, and
		** all the buffers after it (since the tail must be at the
		** end of the file).  We don't want to unmap file data
		** before the tail, since it might be dirty and waiting to
		** reach disk
		*/
		cur_index += bh->b_size ;
		if (cur_index > tail_index) {
		    reiserfs_unmap_buffer(bh) ;
		}
		bh = next ;
	    } while (bh != head) ;
	    if ( PAGE_SIZE == bh->b_size ) {
		clear_page_dirty(page);
	    }
	}
    }
}

static int maybe_indirect_to_direct (struct reiserfs_transaction_handle *th, 
			      struct inode * p_s_inode,
			      struct page *page, 
			      struct path         * p_s_path,
			      const struct cpu_key      * p_s_item_key,
			      loff_t         n_new_file_size,
			      char                * p_c_mode
			      ) {
    struct super_block * p_s_sb = p_s_inode->i_sb;
    int n_block_size = p_s_sb->s_blocksize;
    int cut_bytes;
    BUG_ON (!th->t_trans_id);

    if (n_new_file_size != p_s_inode->i_size)
	BUG ();

    /* the page being sent in could be NULL if there was an i/o error
    ** reading in the last block.  The user will hit problems trying to
    ** read the file, but for now we just skip the indirect2direct
    */
    if (atomic_read(&p_s_inode->i_count) > 1 || 
        !tail_has_to_be_packed (p_s_inode) || 
	!page || (REISERFS_I(p_s_inode)->i_flags & i_nopack_mask)) {
	// leave tail in an unformatted node	
	*p_c_mode = M_SKIP_BALANCING;
	cut_bytes = n_block_size - (n_new_file_size & (n_block_size - 1));
	pathrelse(p_s_path);
	return cut_bytes;
    }
    /* Permorm the conversion to a direct_item. */
    /*return indirect_to_direct (p_s_inode, p_s_path, p_s_item_key, n_new_file_size, p_c_mode);*/
    return indirect2direct (th, p_s_inode, page, p_s_path, p_s_item_key, n_new_file_size, p_c_mode);
}


/* we did indirect_to_direct conversion. And we have inserted direct
   item successesfully, but there were no disk space to cut unfm
   pointer being converted. Therefore we have to delete inserted
   direct item(s) */
static void indirect_to_direct_roll_back (struct reiserfs_transaction_handle *th, struct inode * inode, struct path * path)
{
    struct cpu_key tail_key;
    int tail_len;
    int removed;
    BUG_ON (!th->t_trans_id);

    make_cpu_key (&tail_key, inode, inode->i_size + 1, TYPE_DIRECT, 4);// !!!!
    tail_key.key_length = 4;

    tail_len = (cpu_key_k_offset (&tail_key) & (inode->i_sb->s_blocksize - 1)) - 1;
    while (tail_len) {
	/* look for the last byte of the tail */
	if (search_for_position_by_key (inode->i_sb, &tail_key, path) == POSITION_NOT_FOUND)
	    reiserfs_panic (inode->i_sb, "vs-5615: indirect_to_direct_roll_back: found invalid item");
	RFALSE( path->pos_in_item != ih_item_len(PATH_PITEM_HEAD (path)) - 1,
	        "vs-5616: appended bytes found");
	PATH_LAST_POSITION (path) --;
	
	removed = reiserfs_delete_item (th, path, &tail_key, inode, NULL/*unbh not needed*/);
	RFALSE( removed <= 0 || removed > tail_len,
	        "vs-5617: there was tail %d bytes, removed item length %d bytes",
                tail_len, removed);
	tail_len -= removed;
	set_cpu_key_k_offset (&tail_key, cpu_key_k_offset (&tail_key) - removed);
    }
    reiserfs_warning (inode->i_sb, "indirect_to_direct_roll_back: indirect_to_direct conversion has been rolled back due to lack of disk space");
    //mark_file_without_tail (inode);
    mark_inode_dirty (inode);
}


/* (Truncate or cut entry) or delete object item. Returns < 0 on failure */
int reiserfs_cut_from_item (struct reiserfs_transaction_handle *th, 
			    struct path * p_s_path,
			    struct cpu_key * p_s_item_key,
			    struct inode * p_s_inode,
			    struct page *page, 
			    loff_t n_new_file_size)
{
    struct super_block * p_s_sb = p_s_inode->i_sb;
    /* Every function which is going to call do_balance must first
       create a tree_balance structure.  Then it must fill up this
       structure by using the init_tb_struct and fix_nodes functions.
       After that we can make tree balancing. */
    struct tree_balance s_cut_balance;
    struct item_head *p_le_ih;
    int n_cut_size = 0,        /* Amount to be cut. */
	n_ret_value = CARRY_ON,
	n_removed = 0,     /* Number of the removed unformatted nodes. */
	n_is_inode_locked = 0;
    char                c_mode;            /* Mode of the balance. */
    int retval2 = -1;
    int quota_cut_bytes;
    loff_t tail_pos = 0;

    BUG_ON (!th->t_trans_id);
    
    init_tb_struct(th, &s_cut_balance, p_s_inode->i_sb, p_s_path, n_cut_size);


    /* Repeat this loop until we either cut the item without needing
       to balance, or we fix_nodes without schedule occurring */
    while ( 1 ) {
	/* Determine the balance mode, position of the first byte to
	   be cut, and size to be cut.  In case of the indirect item
	   free unformatted nodes which are pointed to by the cut
	   pointers. */
      
	c_mode = prepare_for_delete_or_cut(th, p_s_inode, p_s_path, p_s_item_key, &n_removed, 
					   &n_cut_size, n_new_file_size);
	if ( c_mode == M_CONVERT )  {
	    /* convert last unformatted node to direct item or leave
               tail in the unformatted node */
	    RFALSE( n_ret_value != CARRY_ON, "PAP-5570: can not convert twice");

	    n_ret_value = maybe_indirect_to_direct (th, p_s_inode, page, p_s_path, p_s_item_key,
						    n_new_file_size, &c_mode);
	    if ( c_mode == M_SKIP_BALANCING )
		/* tail has been left in the unformatted node */
		return n_ret_value;

	    n_is_inode_locked = 1;
	  
	    /* removing of last unformatted node will change value we
               have to return to truncate. Save it */
	    retval2 = n_ret_value;
	    /*retval2 = p_s_sb->s_blocksize - (n_new_file_size & (p_s_sb->s_blocksize - 1));*/
	  
	    /* So, we have performed the first part of the conversion:
	       inserting the new direct item.  Now we are removing the
	       last unformatted node pointer. Set key to search for
	       it. */
      	    set_cpu_key_k_type (p_s_item_key, TYPE_INDIRECT);
	    p_s_item_key->key_length = 4;
	    n_new_file_size -= (n_new_file_size & (p_s_sb->s_blocksize - 1));
	    tail_pos = n_new_file_size;
	    set_cpu_key_k_offset (p_s_item_key, n_new_file_size + 1);
	    if ( search_for_position_by_key(p_s_sb, p_s_item_key, p_s_path) == POSITION_NOT_FOUND ){
		print_block (PATH_PLAST_BUFFER (p_s_path), 3, PATH_LAST_POSITION (p_s_path) - 1, PATH_LAST_POSITION (p_s_path) + 1);
		reiserfs_panic(p_s_sb, "PAP-5580: reiserfs_cut_from_item: item to convert does not exist (%K)", p_s_item_key);
	    }
	    continue;
	}
	if (n_cut_size == 0) {
	    pathrelse (p_s_path);
	    return 0;
	}

	s_cut_balance.insert_size[0] = n_cut_size;
	
	n_ret_value = fix_nodes(c_mode, &s_cut_balance, NULL, NULL);
      	if ( n_ret_value != REPEAT_SEARCH )
	    break;
	
	PROC_INFO_INC( p_s_sb, cut_from_item_restarted );

	n_ret_value = search_for_position_by_key(p_s_sb, p_s_item_key, p_s_path);
	if (n_ret_value == POSITION_FOUND)
	    continue;

	reiserfs_warning (p_s_sb, "PAP-5610: reiserfs_cut_from_item: item %K not found", p_s_item_key);
	unfix_nodes (&s_cut_balance);
	return (n_ret_value == IO_ERROR) ? -EIO : -ENOENT;
    } /* while */
  
    // check fix_nodes results (IO_ERROR or NO_DISK_SPACE)
    if ( n_ret_value != CARRY_ON ) {
	if ( n_is_inode_locked ) {
	    // FIXME: this seems to be not needed: we are always able
	    // to cut item
	    indirect_to_direct_roll_back (th, p_s_inode, p_s_path);
	}
	if (n_ret_value == NO_DISK_SPACE)
	    reiserfs_warning (p_s_sb, "NO_DISK_SPACE");
	unfix_nodes (&s_cut_balance);
	return -EIO;
    }

    /* go ahead and perform balancing */
    
    RFALSE( c_mode == M_PASTE || c_mode == M_INSERT, "invalid mode");

    /* Calculate number of bytes that need to be cut from the item. */
    quota_cut_bytes = ( c_mode == M_DELETE ) ? ih_item_len(get_ih(p_s_path)) : -s_cut_balance.insert_size[0];
    if (retval2 == -1)
	n_ret_value = calc_deleted_bytes_number(&s_cut_balance, c_mode);
    else
	n_ret_value = retval2;


    /* For direct items, we only change the quota when deleting the last
    ** item.
    */
    p_le_ih = PATH_PITEM_HEAD (s_cut_balance.tb_path);
    if (!S_ISLNK (p_s_inode->i_mode) && is_direct_le_ih(p_le_ih)) {
        if (c_mode == M_DELETE &&
	   (le_ih_k_offset (p_le_ih) & (p_s_sb->s_blocksize - 1)) == 1 ) {
	    // FIXME: this is to keep 3.5 happy
	    REISERFS_I(p_s_inode)->i_first_direct_byte = U32_MAX;
	    quota_cut_bytes = p_s_sb->s_blocksize + UNFM_P_SIZE ;
        } else {
	    quota_cut_bytes = 0 ;
	}
    }
#ifdef CONFIG_REISERFS_CHECK
    if (n_is_inode_locked) {
	struct item_head * le_ih = PATH_PITEM_HEAD (s_cut_balance.tb_path);
	/* we are going to complete indirect2direct conversion. Make
           sure, that we exactly remove last unformatted node pointer
           of the item */
	if (!is_indirect_le_ih (le_ih))
	    reiserfs_panic (p_s_sb, "vs-5652: reiserfs_cut_from_item: "
			    "item must be indirect %h", le_ih);

	if (c_mode == M_DELETE && ih_item_len(le_ih) != UNFM_P_SIZE)
	    reiserfs_panic (p_s_sb, "vs-5653: reiserfs_cut_from_item: "
			    "completing indirect2direct conversion indirect item %h "
			    "being deleted must be of 4 byte long", le_ih);

	if (c_mode == M_CUT && s_cut_balance.insert_size[0] != -UNFM_P_SIZE) {
	    reiserfs_panic (p_s_sb, "vs-5654: reiserfs_cut_from_item: "
			    "can not complete indirect2direct conversion of %h (CUT, insert_size==%d)",
			    le_ih, s_cut_balance.insert_size[0]);
	}
	/* it would be useful to make sure, that right neighboring
           item is direct item of this file */
    }
#endif
    
    do_balance(&s_cut_balance, NULL, NULL, c_mode);
    if ( n_is_inode_locked ) {
	/* we've done an indirect->direct conversion.  when the data block
	** was freed, it was removed from the list of blocks that must
	** be flushed before the transaction commits, make sure to
	** unmap and invalidate it
	*/
	unmap_buffers(page, tail_pos);
	REISERFS_I(p_s_inode)->i_flags &= ~i_pack_on_close_mask ;
    }
#ifdef REISERQUOTA_DEBUG
    reiserfs_debug (p_s_inode->i_sb, REISERFS_DEBUG_CODE, "reiserquota cut_from_item(): freeing %u id=%u type=%c", quota_cut_bytes, p_s_inode->i_uid, '?');
#endif
    DQUOT_FREE_SPACE_NODIRTY(p_s_inode, quota_cut_bytes);
    return n_ret_value;
}

static void truncate_directory (struct reiserfs_transaction_handle *th, struct inode * inode)
{
    BUG_ON (!th->t_trans_id);
    if (inode->i_nlink)
	reiserfs_warning (inode->i_sb,
			  "vs-5655: truncate_directory: link count != 0");

    set_le_key_k_offset (KEY_FORMAT_3_5, INODE_PKEY (inode), DOT_OFFSET);
    set_le_key_k_type (KEY_FORMAT_3_5, INODE_PKEY (inode), TYPE_DIRENTRY);
    reiserfs_delete_solid_item (th, inode, INODE_PKEY (inode));
    reiserfs_update_sd(th, inode) ;
    set_le_key_k_offset (KEY_FORMAT_3_5, INODE_PKEY (inode), SD_OFFSET);
    set_le_key_k_type (KEY_FORMAT_3_5, INODE_PKEY (inode), TYPE_STAT_DATA);    
}




/* Truncate file to the new size. Note, this must be called with a transaction
   already started */
int reiserfs_do_truncate (struct reiserfs_transaction_handle *th,
			   struct  inode * p_s_inode, /* ->i_size contains new
                                                         size */
			   struct page *page, /* up to date for last block */
			   int update_timestamps  /* when it is called by
						     file_release to convert
						     the tail - no timestamps
						     should be updated */
    ) {
    INITIALIZE_PATH (s_search_path);       /* Path to the current object item. */
    struct item_head    * p_le_ih;         /* Pointer to an item header. */
    struct cpu_key      s_item_key;     /* Key to search for a previous file item. */
    loff_t         n_file_size,    /* Old file size. */
	n_new_file_size;/* New file size. */
    int                   n_deleted;      /* Number of deleted or truncated bytes. */
    int retval;
    int err = 0;

    BUG_ON (!th->t_trans_id);
    if ( ! (S_ISREG(p_s_inode->i_mode) || S_ISDIR(p_s_inode->i_mode) || S_ISLNK(p_s_inode->i_mode)) )
	return 0;

    if (S_ISDIR(p_s_inode->i_mode)) {
	// deletion of directory - no need to update timestamps
	truncate_directory (th, p_s_inode);
	return 0;
    }

    /* Get new file size. */
    n_new_file_size = p_s_inode->i_size;

    // FIXME: note, that key type is unimportant here
    make_cpu_key (&s_item_key, p_s_inode, max_reiserfs_offset (p_s_inode), TYPE_DIRECT, 3);

    retval = search_for_position_by_key(p_s_inode->i_sb, &s_item_key, &s_search_path);
    if (retval == IO_ERROR) {
	reiserfs_warning (p_s_inode->i_sb, "vs-5657: reiserfs_do_truncate: "
			  "i/o failure occurred trying to truncate %K", &s_item_key);
        err = -EIO;
        goto out;
    }
    if (retval == POSITION_FOUND || retval == FILE_NOT_FOUND) {
	reiserfs_warning (p_s_inode->i_sb, "PAP-5660: reiserfs_do_truncate: "
			  "wrong result %d of search for %K", retval, &s_item_key);

        err = -EIO;
        goto out;
    }

    s_search_path.pos_in_item --;

    /* Get real file size (total length of all file items) */
    p_le_ih = PATH_PITEM_HEAD(&s_search_path);
    if ( is_statdata_le_ih (p_le_ih) )
	n_file_size = 0;
    else {
	loff_t offset = le_ih_k_offset (p_le_ih);
	int bytes = op_bytes_number (p_le_ih,p_s_inode->i_sb->s_blocksize);

	/* this may mismatch with real file size: if last direct item
           had no padding zeros and last unformatted node had no free
           space, this file would have this file size */
	n_file_size = offset + bytes - 1;
    }
    /*
     * are we doing a full truncate or delete, if so
     * kick in the reada code
     */
    if (n_new_file_size == 0)
        s_search_path.reada = PATH_READA | PATH_READA_BACK;

    if ( n_file_size == 0 || n_file_size < n_new_file_size ) {
	goto update_and_out ;
    }

    /* Update key to search for the last file item. */
    set_cpu_key_k_offset (&s_item_key, n_file_size);

    do  {
	/* Cut or delete file item. */
	n_deleted = reiserfs_cut_from_item(th, &s_search_path, &s_item_key, p_s_inode,  page, n_new_file_size);
	if (n_deleted < 0) {
	    reiserfs_warning (p_s_inode->i_sb, "vs-5665: reiserfs_do_truncate: reiserfs_cut_from_item failed");
	    reiserfs_check_path(&s_search_path) ;
	    return 0;
	}

	RFALSE( n_deleted > n_file_size,
		"PAP-5670: reiserfs_cut_from_item: too many bytes deleted: deleted %d, file_size %lu, item_key %K",
		n_deleted, n_file_size, &s_item_key);

	/* Change key to search the last file item. */
	n_file_size -= n_deleted;

	set_cpu_key_k_offset (&s_item_key, n_file_size);

	/* While there are bytes to truncate and previous file item is presented in the tree. */

	/*
	** This loop could take a really long time, and could log 
	** many more blocks than a transaction can hold.  So, we do a polite
	** journal end here, and if the transaction needs ending, we make
	** sure the file is consistent before ending the current trans
	** and starting a new one
	*/
        if (journal_transaction_should_end(th, th->t_blocks_allocated)) {
	  int orig_len_alloc = th->t_blocks_allocated ;
	  decrement_counters_in_path(&s_search_path) ;

	  if (update_timestamps) {
	      p_s_inode->i_mtime = p_s_inode->i_ctime = CURRENT_TIME_SEC;
	  } 
	  reiserfs_update_sd(th, p_s_inode) ;

	  err = journal_end(th, p_s_inode->i_sb, orig_len_alloc) ;
	  if (err)
	    goto out;
	  err = journal_begin (th, p_s_inode->i_sb,
                               JOURNAL_PER_BALANCE_CNT * 6);
	  if (err)
	    goto out;
	  reiserfs_update_inode_transaction(p_s_inode) ;
	}
    } while ( n_file_size > ROUND_UP (n_new_file_size) &&
	      search_for_position_by_key(p_s_inode->i_sb, &s_item_key, &s_search_path) == POSITION_FOUND )  ;

    RFALSE( n_file_size > ROUND_UP (n_new_file_size),
	    "PAP-5680: truncate did not finish: new_file_size %Ld, current %Ld, oid %d",
	    n_new_file_size, n_file_size, s_item_key.on_disk_key.k_objectid);

update_and_out:
    if (update_timestamps) {
	// this is truncate, not file closing
	    p_s_inode->i_mtime = p_s_inode->i_ctime = CURRENT_TIME_SEC;
    }
    reiserfs_update_sd (th, p_s_inode);

out:
    pathrelse(&s_search_path) ;
    return err;
}


#ifdef CONFIG_REISERFS_CHECK
// this makes sure, that we __append__, not overwrite or add holes
static void check_research_for_paste (struct path * path, 
				      const struct cpu_key * p_s_key)
{
    struct item_head * found_ih = get_ih (path);
    
    if (is_direct_le_ih (found_ih)) {
	if (le_ih_k_offset (found_ih) + op_bytes_number (found_ih, get_last_bh (path)->b_size) !=
	    cpu_key_k_offset (p_s_key) ||
	    op_bytes_number (found_ih, get_last_bh (path)->b_size) != pos_in_item (path))
	    reiserfs_panic (NULL, "PAP-5720: check_research_for_paste: "
			    "found direct item %h or position (%d) does not match to key %K",
			    found_ih, pos_in_item (path), p_s_key);
    }
    if (is_indirect_le_ih (found_ih)) {
	if (le_ih_k_offset (found_ih) + op_bytes_number (found_ih, get_last_bh (path)->b_size) != cpu_key_k_offset (p_s_key) || 
	    I_UNFM_NUM (found_ih) != pos_in_item (path) ||
	    get_ih_free_space (found_ih) != 0)
	    reiserfs_panic (NULL, "PAP-5730: check_research_for_paste: "
			    "found indirect item (%h) or position (%d) does not match to key (%K)",
			    found_ih, pos_in_item (path), p_s_key);
    }
}
#endif /* config reiserfs check */


/* Paste bytes to the existing item. Returns bytes number pasted into the item. */
int reiserfs_paste_into_item (struct reiserfs_transaction_handle *th, 
			      struct path         * p_s_search_path,	/* Path to the pasted item.          */
			      const struct cpu_key      * p_s_key,        	/* Key to search for the needed item.*/
			      struct inode	  * inode,		/* Inode item belongs to */
			      const char          * p_c_body,       	/* Pointer to the bytes to paste.    */
			      int                   n_pasted_size)  	/* Size of pasted bytes.             */
{
    struct tree_balance s_paste_balance;
    int                 retval;
    int			fs_gen;

    BUG_ON (!th->t_trans_id);

    fs_gen = get_generation(inode->i_sb) ;

#ifdef REISERQUOTA_DEBUG
    reiserfs_debug (inode->i_sb, REISERFS_DEBUG_CODE, "reiserquota paste_into_item(): allocating %u id=%u type=%c", n_pasted_size, inode->i_uid, key2type(&(p_s_key->on_disk_key)));
#endif

    if (DQUOT_ALLOC_SPACE_NODIRTY(inode, n_pasted_size)) {
	pathrelse(p_s_search_path);
	return -EDQUOT;
    }
    init_tb_struct(th, &s_paste_balance, th->t_super, p_s_search_path, n_pasted_size);
#ifdef DISPLACE_NEW_PACKING_LOCALITIES
    s_paste_balance.key = p_s_key->on_disk_key;
#endif

    /* DQUOT_* can schedule, must check before the fix_nodes */
    if (fs_changed(fs_gen, inode->i_sb)) {
	goto search_again;
    }

    while ((retval = fix_nodes(M_PASTE, &s_paste_balance, NULL, p_c_body)) ==
REPEAT_SEARCH ) {
search_again:
	/* file system changed while we were in the fix_nodes */
	PROC_INFO_INC( th -> t_super, paste_into_item_restarted );
	retval = search_for_position_by_key (th->t_super, p_s_key, p_s_search_path);
	if (retval == IO_ERROR) {
	    retval = -EIO ;
	    goto error_out ;
	}
	if (retval == POSITION_FOUND) {
	    reiserfs_warning (inode->i_sb, "PAP-5710: reiserfs_paste_into_item: entry or pasted byte (%K) exists", p_s_key);
	    retval = -EEXIST ;
	    goto error_out ;
	}
	
#ifdef CONFIG_REISERFS_CHECK
	check_research_for_paste (p_s_search_path, p_s_key);
#endif
    }

    /* Perform balancing after all resources are collected by fix_nodes, and
       accessing them will not risk triggering schedule. */
    if ( retval == CARRY_ON ) {
	do_balance(&s_paste_balance, NULL/*ih*/, p_c_body, M_PASTE);
	return 0;
    }
    retval = (retval == NO_DISK_SPACE) ? -ENOSPC : -EIO;
error_out:
    /* this also releases the path */
    unfix_nodes(&s_paste_balance);
#ifdef REISERQUOTA_DEBUG
    reiserfs_debug (inode->i_sb, REISERFS_DEBUG_CODE, "reiserquota paste_into_item(): freeing %u id=%u type=%c", n_pasted_size, inode->i_uid, key2type(&(p_s_key->on_disk_key)));
#endif
    DQUOT_FREE_SPACE_NODIRTY(inode, n_pasted_size);
    return retval ;
}


/* Insert new item into the buffer at the path. */
int reiserfs_insert_item(struct reiserfs_transaction_handle *th, 
			 struct path         * 	p_s_path,         /* Path to the inserteded item.         */
			 const struct cpu_key      * key,
			 struct item_head    * 	p_s_ih,           /* Pointer to the item header to insert.*/
			 struct inode        * inode,
			 const char          * 	p_c_body)         /* Pointer to the bytes to insert.      */
{
    struct tree_balance s_ins_balance;
    int                 retval;
    int fs_gen = 0 ;
    int quota_bytes = 0 ;

    BUG_ON (!th->t_trans_id);

    if (inode) {      /* Do we count quotas for item? */
	fs_gen = get_generation(inode->i_sb);
	quota_bytes = ih_item_len(p_s_ih);

	/* hack so the quota code doesn't have to guess if the file has
	 ** a tail, links are always tails, so there's no guessing needed
	 */
	if (!S_ISLNK (inode->i_mode) && is_direct_le_ih(p_s_ih)) {
	    quota_bytes = inode->i_sb->s_blocksize + UNFM_P_SIZE ;
	}
#ifdef REISERQUOTA_DEBUG
	reiserfs_debug (inode->i_sb, REISERFS_DEBUG_CODE, "reiserquota insert_item(): allocating %u id=%u type=%c", quota_bytes, inode->i_uid, head2type(p_s_ih));
#endif
	/* We can't dirty inode here. It would be immediately written but
	 * appropriate stat item isn't inserted yet... */
	if (DQUOT_ALLOC_SPACE_NODIRTY(inode, quota_bytes)) {
	    pathrelse(p_s_path);
	    return -EDQUOT;
	}
    }
    init_tb_struct(th, &s_ins_balance, th->t_super, p_s_path, IH_SIZE + ih_item_len(p_s_ih));
#ifdef DISPLACE_NEW_PACKING_LOCALITIES
    s_ins_balance.key = key->on_disk_key;
#endif
    /* DQUOT_* can schedule, must check to be sure calling fix_nodes is safe */
    if (inode && fs_changed(fs_gen, inode->i_sb)) {
	goto search_again;
    }

    while ( (retval = fix_nodes(M_INSERT, &s_ins_balance, p_s_ih, p_c_body)) == REPEAT_SEARCH) {
search_again:
	/* file system changed while we were in the fix_nodes */
	PROC_INFO_INC( th -> t_super, insert_item_restarted );
	retval = search_item (th->t_super, key, p_s_path);
	if (retval == IO_ERROR) {
	    retval = -EIO;
	    goto error_out ;
	}
	if (retval == ITEM_FOUND) {
	    reiserfs_warning (th->t_super, "PAP-5760: reiserfs_insert_item: "
			      "key %K already exists in the tree", key);
	    retval = -EEXIST ;
	    goto error_out; 
	}
    }

    /* make balancing after all resources will be collected at a time */ 
    if ( retval == CARRY_ON ) {
	do_balance (&s_ins_balance, p_s_ih, p_c_body, M_INSERT);
	return 0;
    }

    retval = (retval == NO_DISK_SPACE) ? -ENOSPC : -EIO;
error_out:
    /* also releases the path */
    unfix_nodes(&s_ins_balance);
#ifdef REISERQUOTA_DEBUG
    reiserfs_debug (th->t_super, REISERFS_DEBUG_CODE, "reiserquota insert_item(): freeing %u id=%u type=%c", quota_bytes, inode->i_uid, head2type(p_s_ih));
#endif
    if (inode)
	DQUOT_FREE_SPACE_NODIRTY(inode, quota_bytes) ;
    return retval; 
}




