Commit e3b4a97d authored by Mark Fasheh's avatar Mark Fasheh Committed by Joel Becker

ocfs2: use allocation reservations for directory data

Use the reservations system for unindexed dir tree allocations. We don't
bother with the indexed tree as reads from it are mostly random anyway.
Directory reservations are marked seperately, to allow the reservations code
a chance to optimize their window sizes. This patch allocates only 8 bits
for directory windows as they generally are not expected to grow as quickly
as file data. Future improvements to dir window sizing can trivially be
made.
Signed-off-by: default avatarMark Fasheh <mfasheh@suse.com>
parent 4fe370af
...@@ -2977,6 +2977,7 @@ static int ocfs2_expand_inline_dir(struct inode *dir, struct buffer_head *di_bh, ...@@ -2977,6 +2977,7 @@ static int ocfs2_expand_inline_dir(struct inode *dir, struct buffer_head *di_bh,
* if we only get one now, that's enough to continue. The rest * if we only get one now, that's enough to continue. The rest
* will be claimed after the conversion to extents. * will be claimed after the conversion to extents.
*/ */
data_ac->ac_resv = &oi->ip_la_data_resv;
ret = ocfs2_claim_clusters(osb, handle, data_ac, 1, &bit_off, &len); ret = ocfs2_claim_clusters(osb, handle, data_ac, 1, &bit_off, &len);
if (ret) { if (ret) {
mlog_errno(ret); mlog_errno(ret);
...@@ -3347,6 +3348,8 @@ static int ocfs2_extend_dir(struct ocfs2_super *osb, ...@@ -3347,6 +3348,8 @@ static int ocfs2_extend_dir(struct ocfs2_super *osb,
goto bail; goto bail;
} }
data_ac->ac_resv = &OCFS2_I(dir)->ip_la_data_resv;
credits = ocfs2_calc_extend_credits(sb, el, 1); credits = ocfs2_calc_extend_credits(sb, el, 1);
} else { } else {
spin_unlock(&OCFS2_I(dir)->ip_lock); spin_unlock(&OCFS2_I(dir)->ip_lock);
......
...@@ -377,6 +377,10 @@ void ocfs2_populate_inode(struct inode *inode, struct ocfs2_dinode *fe, ...@@ -377,6 +377,10 @@ void ocfs2_populate_inode(struct inode *inode, struct ocfs2_dinode *fe,
OCFS2_I(inode)->ip_last_used_slot = 0; OCFS2_I(inode)->ip_last_used_slot = 0;
OCFS2_I(inode)->ip_last_used_group = 0; OCFS2_I(inode)->ip_last_used_group = 0;
if (S_ISDIR(inode->i_mode))
ocfs2_resv_set_type(&OCFS2_I(inode)->ip_la_data_resv,
OCFS2_RESV_FLAG_DIR);
mlog_exit_void(); mlog_exit_void();
} }
......
...@@ -44,6 +44,7 @@ DEFINE_SPINLOCK(resv_lock); ...@@ -44,6 +44,7 @@ DEFINE_SPINLOCK(resv_lock);
#define OCFS2_MIN_RESV_WINDOW_BITS 8 #define OCFS2_MIN_RESV_WINDOW_BITS 8
#define OCFS2_MAX_RESV_WINDOW_BITS 1024 #define OCFS2_MAX_RESV_WINDOW_BITS 1024
#define OCFS2_RESV_DIR_WINDOW_BITS OCFS2_MIN_RESV_WINDOW_BITS
static unsigned int ocfs2_resv_window_bits(struct ocfs2_reservation_map *resmap, static unsigned int ocfs2_resv_window_bits(struct ocfs2_reservation_map *resmap,
struct ocfs2_alloc_reservation *resv) struct ocfs2_alloc_reservation *resv)
...@@ -51,8 +52,11 @@ static unsigned int ocfs2_resv_window_bits(struct ocfs2_reservation_map *resmap, ...@@ -51,8 +52,11 @@ static unsigned int ocfs2_resv_window_bits(struct ocfs2_reservation_map *resmap,
struct ocfs2_super *osb = resmap->m_osb; struct ocfs2_super *osb = resmap->m_osb;
unsigned int bits; unsigned int bits;
/* 8, 16, 32, 64, 128, 256, 512, 1024 */ if (!(resv->r_flags & OCFS2_RESV_FLAG_DIR)) {
bits = 4 << osb->osb_resv_level; /* 8, 16, 32, 64, 128, 256, 512, 1024 */
bits = 4 << osb->osb_resv_level;
} else
bits = OCFS2_RESV_DIR_WINDOW_BITS;
return bits; return bits;
} }
......
...@@ -42,6 +42,8 @@ struct ocfs2_alloc_reservation { ...@@ -42,6 +42,8 @@ struct ocfs2_alloc_reservation {
#define OCFS2_RESV_FLAG_INUSE 0x01 /* Set when r_node is part of a btree */ #define OCFS2_RESV_FLAG_INUSE 0x01 /* Set when r_node is part of a btree */
#define OCFS2_RESV_FLAG_TMP 0x02 /* Temporary reservation, will be #define OCFS2_RESV_FLAG_TMP 0x02 /* Temporary reservation, will be
* destroyed immedately after use */ * destroyed immedately after use */
#define OCFS2_RESV_FLAG_DIR 0x04 /* Reservation is for an unindexed
* directory btree */
struct ocfs2_reservation_map { struct ocfs2_reservation_map {
struct rb_root m_reservations; struct rb_root m_reservations;
...@@ -61,7 +63,7 @@ struct ocfs2_reservation_map { ...@@ -61,7 +63,7 @@ struct ocfs2_reservation_map {
void ocfs2_resv_init_once(struct ocfs2_alloc_reservation *resv); void ocfs2_resv_init_once(struct ocfs2_alloc_reservation *resv);
#define OCFS2_RESV_TYPES (OCFS2_RESV_FLAG_TMP) #define OCFS2_RESV_TYPES (OCFS2_RESV_FLAG_TMP|OCFS2_RESV_FLAG_DIR)
void ocfs2_resv_set_type(struct ocfs2_alloc_reservation *resv, void ocfs2_resv_set_type(struct ocfs2_alloc_reservation *resv,
unsigned int flags); unsigned int flags);
......
...@@ -130,6 +130,7 @@ void ocfs2_free_ac_resource(struct ocfs2_alloc_context *ac) ...@@ -130,6 +130,7 @@ void ocfs2_free_ac_resource(struct ocfs2_alloc_context *ac)
} }
brelse(ac->ac_bh); brelse(ac->ac_bh);
ac->ac_bh = NULL; ac->ac_bh = NULL;
ac->ac_resv = NULL;
} }
void ocfs2_free_alloc_context(struct ocfs2_alloc_context *ac) void ocfs2_free_alloc_context(struct ocfs2_alloc_context *ac)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment