Esempio n. 1
0
static int nilfs_direct_propagate(struct nilfs_bmap *bmap,
				  struct buffer_head *bh)
{
	struct nilfs_palloc_req oldreq, newreq;
	struct inode *dat;
	__u64 key;
	__u64 ptr;
	int ret;

	if (!NILFS_BMAP_USE_VBN(bmap))
		return 0;

	dat = nilfs_bmap_get_dat(bmap);
	key = nilfs_bmap_data_get_key(bmap, bh);
	ptr = nilfs_direct_get_ptr(bmap, key);
	if (!buffer_nilfs_volatile(bh)) {
		oldreq.pr_entry_nr = ptr;
		newreq.pr_entry_nr = ptr;
		ret = nilfs_dat_prepare_update(dat, &oldreq, &newreq);
		if (ret < 0)
			return ret;
		nilfs_dat_commit_update(dat, &oldreq, &newreq,
					bmap->b_ptr_type == NILFS_BMAP_PTR_VS);
		set_buffer_nilfs_volatile(bh);
		nilfs_direct_set_ptr(bmap, key, newreq.pr_entry_nr);
	} else
		ret = nilfs_dat_mark_dirty(dat, ptr);

	return ret;
}
Esempio n. 2
0
static int nilfs_direct_insert(struct nilfs_bmap *bmap, __u64 key, __u64 ptr)
{
	union nilfs_bmap_ptr_req req;
	struct inode *dat = NULL;
	struct buffer_head *bh;
	int ret;

	if (key > NILFS_DIRECT_KEY_MAX)
		return -ENOENT;
	if (nilfs_direct_get_ptr(bmap, key) != NILFS_BMAP_INVALID_PTR)
		return -EEXIST;

	if (NILFS_BMAP_USE_VBN(bmap)) {
		req.bpr_ptr = nilfs_direct_find_target_v(bmap, key);
		dat = nilfs_bmap_get_dat(bmap);
	}
	ret = nilfs_bmap_prepare_alloc_ptr(bmap, &req, dat);
	if (!ret) {
		/* ptr must be a pointer to a buffer head. */
		bh = (struct buffer_head *)((unsigned long)ptr);
		set_buffer_nilfs_volatile(bh);

		nilfs_bmap_commit_alloc_ptr(bmap, &req, dat);
		nilfs_direct_set_ptr(bmap, key, req.bpr_ptr);

		if (!nilfs_bmap_dirty(bmap))
			nilfs_bmap_set_dirty(bmap);

		if (NILFS_BMAP_USE_VBN(bmap))
			nilfs_bmap_set_target_v(bmap, key, req.bpr_ptr);

		nilfs_inode_add_blocks(bmap->b_inode, 1);
	}
	return ret;
}
Esempio n. 3
0
static void nilfs_bmap_commit_start_v(struct nilfs_bmap *bmap,
				      union nilfs_bmap_ptr_req *req,
				      sector_t blocknr)
{
	nilfs_dat_commit_start(nilfs_bmap_get_dat(bmap), &req->bpr_req,
			       blocknr);
}
Esempio n. 4
0
__u64 nilfs_bmap_find_target_in_group(const struct nilfs_bmap *bmap)
{
	struct inode *dat = nilfs_bmap_get_dat(bmap);
	unsigned long entries_per_group = nilfs_palloc_entries_per_group(dat);
	unsigned long group = bmap->b_inode->i_ino / entries_per_group;

	return group * entries_per_group +
		(bmap->b_inode->i_ino % NILFS_BMAP_GROUP_DIV) *
		(entries_per_group / NILFS_BMAP_GROUP_DIV);
}
Esempio n. 5
0
static int nilfs_bmap_translate_v(const struct nilfs_bmap *bmap, __u64 ptr,
				  __u64 *ptrp)
{
	sector_t blocknr;
	int ret;

	ret = nilfs_dat_translate(nilfs_bmap_get_dat(bmap), ptr, &blocknr);
	if (ret < 0)
		return ret;
	if (ptrp != NULL)
		*ptrp = blocknr;
	return 0;
}
Esempio n. 6
0
static int nilfs_direct_assign_v(struct nilfs_bmap *direct,
				 __u64 key, __u64 ptr,
				 struct buffer_head **bh,
				 sector_t blocknr,
				 union nilfs_binfo *binfo)
{
	struct inode *dat = nilfs_bmap_get_dat(direct);
	union nilfs_bmap_ptr_req req;
	int ret;

	req.bpr_ptr = ptr;
	ret = nilfs_dat_prepare_start(dat, &req.bpr_req);
	if (!ret) {
		nilfs_dat_commit_start(dat, &req.bpr_req, blocknr);
		binfo->bi_v.bi_vblocknr = cpu_to_le64(ptr);
		binfo->bi_v.bi_blkoff = cpu_to_le64(key);
	}
	return ret;
}
Esempio n. 7
0
static int nilfs_direct_lookup_contig(const struct nilfs_bmap *bmap,
				      __u64 key, __u64 *ptrp,
				      unsigned maxblocks)
{
	struct nilfs_direct *direct = (struct nilfs_direct *)bmap;
	struct inode *dat = NULL;
	__u64 ptr, ptr2;
	sector_t blocknr;
	int ret, cnt;

	if (key > NILFS_DIRECT_KEY_MAX)
		return -ENOENT;
	ptr = nilfs_direct_get_ptr(direct, key);
	if (ptr == NILFS_BMAP_INVALID_PTR)
		return -ENOENT;

	if (NILFS_BMAP_USE_VBN(bmap)) {
		dat = nilfs_bmap_get_dat(bmap);
		ret = nilfs_dat_translate(dat, ptr, &blocknr);
		if (ret < 0)
			return ret;
		ptr = blocknr;
	}

	maxblocks = min_t(unsigned, maxblocks, NILFS_DIRECT_KEY_MAX - key + 1);
	for (cnt = 1; cnt < maxblocks &&
		     (ptr2 = nilfs_direct_get_ptr(direct, key + cnt)) !=
		     NILFS_BMAP_INVALID_PTR;
	     cnt++) {
		if (dat) {
			ret = nilfs_dat_translate(dat, ptr2, &blocknr);
			if (ret < 0)
				return ret;
			ptr2 = blocknr;
		}
		if (ptr2 != ptr + cnt)
			break;
	}
	*ptrp = ptr;
	return cnt;
}
Esempio n. 8
0
/**
 * nilfs_bmap_lookup_at_level - find a data block or node block
 * @bmap: bmap
 * @key: key
 * @level: level
 * @ptrp: place to store the value associated to @key
 *
 * Description: nilfs_bmap_lookup_at_level() finds a record whose key
 * matches @key in the block at @level of the bmap.
 *
 * Return Value: On success, 0 is returned and the record associated with @key
 * is stored in the place pointed by @ptrp. On error, one of the following
 * negative error codes is returned.
 *
 * %-EIO - I/O error.
 *
 * %-ENOMEM - Insufficient amount of memory available.
 *
 * %-ENOENT - A record associated with @key does not exist.
 */
int nilfs_bmap_lookup_at_level(struct nilfs_bmap *bmap, __u64 key, int level,
			       __u64 *ptrp)
{
	sector_t blocknr;
	int ret;

	down_read(&bmap->b_sem);
	ret = bmap->b_ops->bop_lookup(bmap, key, level, ptrp);
	if (ret < 0)
		goto out;
	if (NILFS_BMAP_USE_VBN(bmap)) {
		ret = nilfs_dat_translate(nilfs_bmap_get_dat(bmap), *ptrp,
					  &blocknr);
		if (!ret)
			*ptrp = blocknr;
	}

 out:
	up_read(&bmap->b_sem);
	return ret;
}
Esempio n. 9
0
static int nilfs_direct_delete(struct nilfs_bmap *bmap, __u64 key)
{
	union nilfs_bmap_ptr_req req;
	struct inode *dat;
	int ret;

	if (key > NILFS_DIRECT_KEY_MAX ||
	    nilfs_direct_get_ptr(bmap, key) == NILFS_BMAP_INVALID_PTR)
		return -ENOENT;

	dat = NILFS_BMAP_USE_VBN(bmap) ? nilfs_bmap_get_dat(bmap) : NULL;
	req.bpr_ptr = nilfs_direct_get_ptr(bmap, key);

	ret = nilfs_bmap_prepare_end_ptr(bmap, &req, dat);
	if (!ret) {
		nilfs_bmap_commit_end_ptr(bmap, &req, dat);
		nilfs_direct_set_ptr(bmap, key, NILFS_BMAP_INVALID_PTR);
		nilfs_inode_sub_blocks(bmap->b_inode, 1);
	}
	return ret;
}
Esempio n. 10
0
int nilfs_bmap_mark_dirty(const struct nilfs_bmap *bmap, __u64 vblocknr)
{
	return nilfs_dat_mark_dirty(nilfs_bmap_get_dat(bmap), vblocknr);
}
Esempio n. 11
0
int nilfs_bmap_move_v(const struct nilfs_bmap *bmap, __u64 vblocknr,
		      sector_t blocknr)
{
	return nilfs_dat_move(nilfs_bmap_get_dat(bmap), vblocknr, blocknr);
}
Esempio n. 12
0
static void nilfs_bmap_abort_end_v(struct nilfs_bmap *bmap,
				   union nilfs_bmap_ptr_req *req)
{
	nilfs_dat_abort_end(nilfs_bmap_get_dat(bmap), &req->bpr_req);
}
Esempio n. 13
0
static void nilfs_bmap_commit_end_vmdt(struct nilfs_bmap *bmap,
				       union nilfs_bmap_ptr_req *req)
{
	nilfs_dat_commit_end(nilfs_bmap_get_dat(bmap), &req->bpr_req, 1);
}
Esempio n. 14
0
static int nilfs_bmap_prepare_end_v(struct nilfs_bmap *bmap,
				    union nilfs_bmap_ptr_req *req)
{
	return nilfs_dat_prepare_end(nilfs_bmap_get_dat(bmap), &req->bpr_req);
}
Esempio n. 15
0
static void nilfs_bmap_commit_alloc_v(struct nilfs_bmap *bmap,
				      union nilfs_bmap_ptr_req *req)
{
	nilfs_dat_commit_alloc(nilfs_bmap_get_dat(bmap), &req->bpr_req);
}