[Ocfs2-commits] mfasheh commits r845 - in branches/nooin/src: . inc
svn-commits at oss.oracle.com
svn-commits at oss.oracle.com
Thu Apr 15 21:28:19 CDT 2004
Author: mfasheh
Date: 2004-04-15 20:28:18 -0500 (Thu, 15 Apr 2004)
New Revision: 845
Modified:
branches/nooin/src/dlm.c
branches/nooin/src/extmap.c
branches/nooin/src/file.c
branches/nooin/src/hash.c
branches/nooin/src/inc/journal.h
branches/nooin/src/inc/ocfs.h
branches/nooin/src/inc/proto.h
branches/nooin/src/inode.c
branches/nooin/src/journal.c
branches/nooin/src/namei.c
branches/nooin/src/nm.c
branches/nooin/src/oin.c
branches/nooin/src/super.c
Log:
* finally move oin into the inode. This is a big patch, which also
fixed a couple bugs which I found along the way (one in rename and one
having to do with adding ourselves to the oin list during an open)
Modified: branches/nooin/src/dlm.c
===================================================================
--- branches/nooin/src/dlm.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/dlm.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -37,7 +37,6 @@
static inline int ocfs_wait_for_readonly_drop(ocfs_super *osb, ocfs_lock_res *lockres, struct inode *inode);
-static int ocfs_insert_cache_link (ocfs_super * osb, ocfs_lock_res * lockres);
static int ocfs_send_dlm_request_msg (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, ocfs_lock_res * lockres, __u64 vote_map, struct inode *inode);
static int ocfs_request_vote (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, __u64 vote_map, __u64 * lock_seq_num, struct inode *inode);
static int ocfs_wait_for_vote (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, __u64 vote_map, __u32 time_to_wait, __u64 lock_seq_num, ocfs_lock_res * lockres);
@@ -46,32 +45,12 @@
static int ocfs_get_vote_on_disk (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, __u64 * got_vote_map, __u64 vote_map, __u64 lock_seq_num, __u64 * oin_open_map);
static int ocfs_break_cache_lock (ocfs_super * osb, ocfs_lock_res * lockres, struct inode *inode);
static int ocfs_disk_request_vote (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, __u64 vote_map, __u64 * lock_seq_num, __u64 feoff);
-int ocfs_update_disk_lock (ocfs_super * osb, ocfs_lock_res * lockres, __u32 flags, struct buffer_head **bh, struct inode *inode);
-static int ocfs_update_master_on_open (ocfs_super * osb, ocfs_lock_res * lockres, struct inode *inode);
+int ocfs_update_disk_lock (ocfs_super * osb, ocfs_lock_res * lockres, __u32 flags, struct buffer_head **bh, struct inode *inode, ocfs_journal_handle *handle);
+static int ocfs_update_master_on_open (ocfs_super * osb, ocfs_lock_res * lockres, struct inode *inode, ocfs_journal_handle *handle);
int ocfs_disk_release_lock (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, ocfs_lock_res * lockres, struct buffer_head *bh, struct inode *inode);
static int ocfs_zap_child_buffers_func(struct dentry *dentry, void *data);
/*
- * ocfs_insert_cache_link()
- *
- */
-static int ocfs_insert_cache_link (ocfs_super * osb, ocfs_lock_res * lockres)
-{
- int status = 0;
-
- LOG_ENTRY ();
-
- lockres->in_cache_list = true;
-
- list_add_tail (&(lockres->cache_list), &(osb->cache_lock_list));
-
- LOG_EXIT_STATUS (status);
- return status;
-} /* ocfs_insert_cache_link */
-
-
-
-/*
* ocfs_disk_request_vote()
*
*/
@@ -812,6 +791,9 @@
unsigned long jif = 0;
int status = 0;
int cnt = 0;
+#ifdef VERBOSE_LOCKING_TRACE
+ bool printed = false;
+#endif
LOG_ENTRY_ARGS ("(0x%08x, %d)\n", lockres, timeout);
@@ -826,6 +808,12 @@
if (lockres->in_use) {
if (lockres->thread_id != mypid) {
spin_unlock (&lockres->lock_mutex);
+#ifdef VERBOSE_LOCKING_TRACE
+ if (!printed) {
+ printk("ocfs2: waiting on lockres %u.%u, mypid = %u, thread_id = %u\n", HILO(lockres->sector_num), ocfs_getpid(), lockres->thread_id);
+ printed = true;
+ }
+#endif
if (jif && jif < jiffies) {
LOG_TRACE_ARGS ("lockpid=%d, newpid=%d,"
" timedout\n",
@@ -890,7 +878,7 @@
* ocfs_update_disk_lock()
*
*/
-int ocfs_update_disk_lock (ocfs_super * osb, ocfs_lock_res * lockres, __u32 flags, struct buffer_head **bh, struct inode *inode)
+int ocfs_update_disk_lock (ocfs_super * osb, ocfs_lock_res * lockres, __u32 flags, struct buffer_head **bh, struct inode *inode, ocfs_journal_handle *handle)
{
int status = 0;
__u64 offset = 0;
@@ -905,6 +893,15 @@
LOG_ERROR_STATUS (status);
goto finally;
}
+
+ if (handle) {
+ status = ocfs_journal_access(handle, *bh, OCFS_JOURNAL_ACCESS_WRITE);
+ if (status < 0) {
+ LOG_ERROR_STATUS (status);
+ goto finally;
+ }
+ }
+
fe = (ocfs_file_entry *)OCFS_BH_GET_DATA_READ(*bh); /* read */
if (flags & DLOCK_FLAG_MASTER &&
@@ -950,7 +947,16 @@
OCFS_BH_PUT_DATA(*bh);
if (changed) {
- status = ocfs_write_bh (osb, *bh, 0, inode);
+ if (handle) {
+ status = ocfs_journal_dirty(handle, *bh);
+ lockres->lock_holders++;
+#warning I hope these lock flags are alright.
+ ocfs_get_lockres(lockres);
+ ocfs_journal_add_lock(handle, lockres->sector_num,
+ lockres->lock_type, 0, lockres,
+ *bh, inode);
+ } else
+ status = ocfs_write_bh (osb, *bh, 0, inode);
if (status < 0)
LOG_ERROR_STATUS (status);
}
@@ -964,7 +970,7 @@
* ocfs_update_master_on_open()
*
*/
-int ocfs_update_master_on_open (ocfs_super * osb, ocfs_lock_res * lockres, struct inode *inode)
+int ocfs_update_master_on_open (ocfs_super * osb, ocfs_lock_res * lockres, struct inode *inode, ocfs_journal_handle *handle)
{
int status = -EAGAIN;
bool disk_vote = false;
@@ -991,7 +997,8 @@
lockres->oin_openmap |= (1 << osb->node_num);
status = ocfs_update_disk_lock (osb, lockres,
- DLOCK_FLAG_OPEN_MAP, &bh, inode);
+ DLOCK_FLAG_OPEN_MAP, &bh,
+ inode, handle);
if (bh)
brelse(bh);
@@ -1045,7 +1052,6 @@
lockres->oin_openmap = 0;
lockres->sector_num = lock_id;
lockres->in_use = 0;
- lockres->oin = NULL;
lockres->lock_state = 0;
lockres->vote_state = 0;
lockres->in_cache_list = false;
@@ -1080,7 +1086,7 @@
* ocfs_create_update_lock()
*
*/
-int ocfs_create_update_lock (ocfs_super * osb, ocfs_inode * oin, __u64 lock_id, __u32 flags, bool new_file, struct inode *inode)
+int ocfs_create_update_lock (ocfs_super * osb, ocfs_inode * oin, __u64 lock_id, __u32 flags, bool new_file, struct inode *inode, ocfs_journal_handle *handle)
{
int status = 0;
ocfs_lock_res *lockres = NULL;
@@ -1101,17 +1107,6 @@
}
ocfs_acquire_lockres (lockres);
- if (lockres->oin) {
- if (lockres->oin->obj_id.type != OCFS_TYPE_OIN) {
- ocfs_release_lockres (lockres);
- LOG_ERROR_STATUS (status = -EFAIL);
- goto bail;
- } else {
- ocfs_put_lockres (lockres->oin->lock_res);
- lockres->oin->lock_res = NULL;
- }
- }
- lockres->oin = oin;
oin->oin_flags |= flags;
ocfs_get_lockres (lockres);
oin->lock_res = lockres;
@@ -1168,20 +1163,11 @@
}
goto bail;
}
- } else {
- if (flags & OCFS_OIN_CACHE_UPDATE) {
- status = ocfs_insert_cache_link (osb, lockres);
- if (status < 0) {
- LOG_ERROR_STR ("Lock up volume");
- goto bail;
- }
- }
}
}
ocfs_acquire_lockres (lockres);
- lockres->oin = oin;
oin->oin_flags |= flags;
if (oin->lock_res != lockres) {
ocfs_put_lockres (oin->lock_res);
@@ -1199,7 +1185,7 @@
/* Send a message to master so that he can send the oin update to */
/* this node also. If u are the master then update File_entry */
/* and set the bit that this node has a open */
- status = ocfs_update_master_on_open (osb, lockres, inode);
+ status = ocfs_update_master_on_open (osb, lockres, inode, handle);
if (status < 0) {
ocfs_release_lockres (lockres);
if (status != -EINTR)
@@ -2082,7 +2068,7 @@
/* update the disk lock */
if (need_lock_write) {
- status = ocfs_update_disk_lock (osb, lockres, lock_write_flags, &bh, inode);
+ status = ocfs_update_disk_lock (osb, lockres, lock_write_flags, &bh, inode, NULL);
if (status < 0)
LOG_ERROR_STATUS (status);
}
Modified: branches/nooin/src/extmap.c
===================================================================
--- branches/nooin/src/extmap.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/extmap.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -439,7 +439,7 @@
* ocfs_delete_all_extent_maps()
*
*/
-void ocfs_delete_all_extent_maps (ocfs_inode * oin)
+void ocfs_delete_all_extent_maps (ocfs_super *osb, ocfs_inode * oin)
{
__u32 RunsInExtentMap = 0, ExtentMapIndex, ByteCount = 0;
__s64 Vbo;
@@ -452,9 +452,9 @@
for (ExtentMapIndex = 0; ExtentMapIndex < RunsInExtentMap;
ExtentMapIndex++) {
if (ocfs_get_next_extent_map_entry
- (oin->osb, &oin->map, ExtentMapIndex, &Vbo, &Lbo,
+ (osb, &oin->map, ExtentMapIndex, &Vbo, &Lbo,
&ByteCount)) {
- ocfs_remove_extent_map_entry (oin->osb, &oin->map, Vbo,
+ ocfs_remove_extent_map_entry (osb, &oin->map, Vbo,
ByteCount);
}
}
Modified: branches/nooin/src/file.c
===================================================================
--- branches/nooin/src/file.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/file.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -96,7 +96,6 @@
ocfs_inode *oin = NULL;
bool bAcquiredOIN = false;
bool bClearInUse = false;
- bool new_oin = false;
struct buffer_head *fe_bh = NULL;
__u64 parent_off;
ocfs_sem *oin_sem = NULL;
@@ -121,98 +120,60 @@
/* kch - for an open request we are already given the
* inode, and therefore we are given the oin too */
down(&inode->i_sem);
- oin = NULL;
- if (inode_data_is_oin (inode))
- oin = GET_INODE_OIN(inode);
- status = -EFAIL;
+ oin = GET_INODE_OIN(inode);
+ oin_sem = &(oin->main_res);
+ ocfs_down_sem (oin_sem, true);
+ bAcquiredOIN = true;
- if (oin != NULL) {
- if (!(oin->oin_flags & OCFS_OIN_IN_TEARDOWN) &&
- !(oin->oin_flags & OCFS_OIN_DELETE_ON_CLOSE)) {
- OCFS_SET_FLAG (oin->oin_flags, OCFS_OIN_IN_USE);
- status = 0;
- }
- if (status < 0) {
- if (oin->oin_flags & OCFS_OIN_IN_TEARDOWN)
- LOG_ERROR_ARGS ("oin (%p) in teardown", oin);
- else
- LOG_ERROR_ARGS ("oin (%p) deleted", oin);
- }
+ /* If the in use flag is set, forget about it. This will go
+ * eventually. */
+ if (!(oin->oin_flags & OCFS_OIN_IN_TEARDOWN) &&
+ !(oin->oin_flags & OCFS_OIN_DELETE_ON_CLOSE)) {
+ OCFS_SET_FLAG (oin->oin_flags, OCFS_OIN_IN_USE);
+ bClearInUse = true;
} else {
- /* now it IS possible to have an inode but no OIN attached yet
- * must be loaded now to open file */
- status = -ENOENT;
+ if (oin->oin_flags & OCFS_OIN_IN_TEARDOWN)
+ LOG_ERROR_ARGS ("oin (%p) in teardown", oin);
+ else
+ LOG_ERROR_ARGS ("oin (%p) deleted", oin);
+ up(&inode->i_sem);
+ goto leave;
}
- up(&inode->i_sem);
- if (status < 0) {
- if (status != -ENOENT && status != -EINTR) {
- LOG_ERROR_STATUS (status);
+ /* first open, we've gotta update the lock state. */
+ if (!oin->open_hndl_cnt) {
+ status = ocfs_read_bh(osb, GET_INODE_FEOFF(inode), &fe_bh,
+ OCFS_BH_CACHED, inode);
+ if (status < 0) {
+ up(&inode->i_sem);
+ LOG_ERROR_STATUS(status);
goto leave;
}
- /* Look on the disk now ... */
- down(&parent->i_sem);
- status = ocfs_find_files_on_disk (osb, parent_off, &(dentry->d_name),
- &fe_bh, NULL, parent, true);
- up(&parent->i_sem);
-
- if (status >= 0) {
- oin = NULL;
- ocfs_down_sem (&(osb->osb_res), true);
- status = ocfs_create_oin_from_entry (osb, fe_bh, &oin, parent_off, inode);
- if (status < 0)
- LOG_ERROR_STATUS(status);
- new_oin = true;
- ocfs_up_sem (&(osb->osb_res));
+ status = ocfs_inode_open(osb, fe_bh, NULL, inode);
+ if (status < 0) {
+ up(&inode->i_sem);
+ LOG_ERROR_STATUS(status);
+ if (status != -EINTR) {
+ LOG_ERROR_ARGS("Open request made for nonexistent "
+ "file! ('%*s')",
+ file->f_dentry->d_name.len,
+ file->f_dentry->d_name.name);
+ status = -ENOENT;
+ }
+ goto leave;
}
- }
+ bClearInUse = true;
- if (status < 0) { /* not found on disk or in mem */
- if (status != -EINTR) {
- LOG_ERROR_ARGS("Open request made for nonexistent "
- "file! ('%*s')",
- file->f_dentry->d_name.len,
- file->f_dentry->d_name.name);
- status = -ENOENT;
+ status = ocfs_inode_fill_ext_map (osb, fe_bh, inode);
+ if (status < 0) {
+ up(&inode->i_sem);
+ LOG_ERROR_STATUS(status);
+ goto leave;
}
- goto leave;
}
-
- bClearInUse = true;
-
- /* check if another process doing an open */
- /* concurrently has just set the oin */
- down(&inode->i_sem);
- if (new_oin) {
- if (inode_data_is_oin (inode)) {
- // delete the oin we just made
- if (oin->inode) {
- iput(oin->inode);
- oin->inode = NULL;
- }
- oin->lock_res = NULL;
- ocfs_release_oin(oin, true);
- // and use the correct one
- oin = GET_INODE_OIN(inode);
- } else {
- if (ocfs_inc_icount(inode) < 0)
- BUG();
- oin->inode = inode;
- SET_INODE_OIN (inode, oin);
- }
- }
-
- /* we should now have a single oin regardless */
- /* of how many concurrent openers at this point */
- /* so take the oin->main_res so we won't need the i_sem */
up(&inode->i_sem);
-
- oin_sem = &(oin->main_res);
- if (!bAcquiredOIN) {
- ocfs_down_sem (oin_sem, true);
- bAcquiredOIN = true;
- }
+ /* yes, hold onto main_res. */
if (oin->oin_flags & OCFS_OIN_DELETE_ON_CLOSE) {
LOG_TRACE_STR ("oin has DELETE_ON_CLOSE set, returning DELETE_PENDING");
@@ -326,6 +287,9 @@
ret = 0;
}
+ if (ret < 0)
+ ocfs_bh_sem_hash_cleanup_pid(ocfs_getpid());
+
LOG_TRACE_ARGS
("exiting file_open: file=%p dentry=%p inode=%p oin=%p kiovec=%d\n",
file, file->f_dentry, file->f_dentry->d_inode,
@@ -375,18 +339,14 @@
ocfs_safefree (ofile->curr_dir_buf);
ofile->curr_dir_buf = NULL;
}
- ocfs_release_ofile (ofile);
+ BUG();
+ ocfs_release_ofile (ofile);
}
goto bail;
}
- /* file */
- if (inode_data_is_oin(inode))
- oin = GET_INODE_OIN(inode);
+ oin = GET_INODE_OIN(inode);
- if (oin == NULL)
- goto bail;
-
if (oin->obj_id.type != OCFS_TYPE_OIN ||
oin->obj_id.size != sizeof (ocfs_inode) ||
oin->main_res.magic != OCFS_SEM_MAGIC) {
@@ -411,32 +371,33 @@
ocfs_up_sem (&(oin->main_res));
goto bail;
}
-
+
LOG_TRACE_ARGS ("openhandles: %d / osbfiles: %d / refcount: %d\n",
oin->open_hndl_cnt, osb->file_open_cnt,
atomic_read(&dentry->d_count));
-
- /* FIXME: in all the other places I run thru all the dentries */
- /* for the inode, but here I just check this one becuz I'm lz */
- /* no hard links yet so who cares */
- if (!atomic_read(&dentry->d_count)) {
- if (oin->oin_flags & OCFS_OIN_OPEN_FOR_DIRECTIO) {
+
+ if (last_close) {
+ ocfs_extent_map_destroy (&oin->map);
+ ocfs_extent_map_init (&oin->map);
+
+ if (oin->oin_flags & OCFS_OIN_OPEN_FOR_DIRECTIO)
OCFS_CLEAR_FLAG(oin->oin_flags, OCFS_OIN_OPEN_FOR_DIRECTIO);
+
+ if (oin->oin_flags & OCFS_OIN_NEEDS_DELETION ||
+ oin->oin_flags & OCFS_OIN_IN_USE) {
+ ocfs_up_sem (&(oin->main_res));
+ LOG_ERROR_STR("Not deleting lockrse on a last close! eek!");
+ goto bail;
}
- if (oin->oin_flags & OCFS_OIN_NEEDS_DELETION ||
- oin->oin_flags & OCFS_OIN_IN_USE) {
- ocfs_up_sem (&(oin->main_res));
- goto bail;
- }
-
- ocfs_up_sem (&(oin->main_res));
- ocfs_release_oin (oin, true);
- ocfs_sync_inode(inode);
- } else {
- ocfs_up_sem (&(oin->main_res));
- ocfs_release_cached_oin (osb, oin);
- ocfs_sync_inode(inode);
- }
+ if (!oin->lock_res)
+ LOG_ERROR_STR("My oin has no lockres!");
+ else {
+ ocfs_put_lockres(oin->lock_res);
+ oin->lock_res = NULL;
+ }
+ }
+ ocfs_up_sem (&(oin->main_res));
+ ocfs_sync_inode(inode);
if (last_close) {
if (inode->i_data.nrpages)
@@ -444,6 +405,8 @@
}
bail:
+// ocfs_bh_sem_hash_cleanup_pid(ocfs_getpid());
+
LOG_EXIT_LONG (0);
return 0;
} /* ocfs_file_release */
@@ -657,7 +620,7 @@
goto bail;
}
oin = GET_INODE_OIN(inode);
- osb = (ocfs_super *) oin->osb;
+ osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
lockres = oin->lock_res;
if (lockres == NULL) {
@@ -750,7 +713,7 @@
HI (oin->alloc_size), LO (oin->alloc_size), HI (newsize),
LO (newsize));
- status = ocfs_extend_file (osb, oin->parent_dirnode_off, oin, newsize, GET_INODE_FEOFF(inode), NULL, inode, NULL);
+ status = ocfs_extend_file (osb, oin, newsize, GET_INODE_FEOFF(inode), NULL, inode, NULL);
if (status < 0) {
if (status != -EINTR && status != -ENOSPC) {
LOG_ERROR_STATUS (status);
@@ -791,7 +754,7 @@
}
ocfs_put_lockres (lockres);
-
+
if (ret < 0)
ocfs_bh_sem_hash_cleanup_pid(ocfs_getpid());
@@ -822,7 +785,7 @@
goto bail;
}
oin = GET_INODE_OIN(inode);
- osb = (ocfs_super *) oin->osb;
+ osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
if (filp->f_flags & O_DIRECT) {
/* anything special for o_direct? */
@@ -1066,7 +1029,7 @@
/* ocfs_extend_file()
*
*/
-int ocfs_extend_file (ocfs_super * osb, __u64 parent_off, ocfs_inode * oin, __u64 file_size, __u64 file_off, ocfs_journal_handle *passed_handle, struct inode *inode, struct iattr *attr)
+int ocfs_extend_file (ocfs_super * osb, ocfs_inode * oin, __u64 file_size, __u64 file_off, ocfs_journal_handle *passed_handle, struct inode *inode, struct iattr *attr)
{
int status = 0;
int tmpstat;
@@ -1404,7 +1367,7 @@
status = ocfs_truncate_file(osb, fileOff, newsize,
oin, inode);
else {
- status = ocfs_extend_file(osb, parentOff, oin, newsize,
+ status = ocfs_extend_file(osb, oin, newsize,
fileOff, NULL, inode, attr);
extended = true;
}
@@ -1418,7 +1381,7 @@
if (oin != NULL) {
ocfs_down_sem (&(oin->main_res), true);
if (inode->i_size > newsize) {
- ocfs_delete_all_extent_maps(oin);
+ ocfs_delete_all_extent_maps(osb, oin);
}
inode->i_size = newsize;
inode->i_blocks = (newsize + sb->s_blocksize) >> sb->s_blocksize_bits;
@@ -1507,6 +1470,7 @@
struct inode *inode;
struct super_block *sb = dentry->d_inode->i_sb;
int status, needs_trunc = 0;
+ ocfs_super *osb;
LOG_ENTRY_ARGS ("(0x%08x, 0x%08x, '%*s')\n", dentry, attr,
dentry->d_name.len, dentry->d_name.name);
@@ -1514,12 +1478,14 @@
inode = dentry->d_inode;
if (inode == NULL || !inode_data_is_oin (inode))
goto bail;
+
+ osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
oin = GET_INODE_OIN(inode);
if (oin == ((ocfs_super *)(OCFS_GENERIC_SB_P(sb)))->oin_root_dir)
goto bail;
if (oin != NULL) {
ocfs_down_sem (&(oin->main_res), true);
- status = ocfs_verify_update_oin (oin->osb, oin, &needs_trunc);
+ status = ocfs_verify_update_oin (osb, oin, &needs_trunc);
ocfs_up_sem (&(oin->main_res));
if (needs_trunc)
ocfs_truncate_inode_pages(inode, 0);
Modified: branches/nooin/src/hash.c
===================================================================
--- branches/nooin/src/hash.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/hash.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -1526,7 +1526,7 @@
inum = __ocfs_inode_hash_lookup(h, voteoff);
if (!inum) {
- printk("ocfs2: lost inum, offset =%u.%u, inode->i_ino= %lu\n",
+ printk("ocfs2: lost inum, offset = %u.%u, inode->i_ino= %lu\n",
HILO(voteoff), inode->i_ino);
BUG();
Modified: branches/nooin/src/inc/journal.h
===================================================================
--- branches/nooin/src/inc/journal.h 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/inc/journal.h 2004-04-16 01:28:18 UTC (rev 845)
@@ -395,4 +395,8 @@
+ OCFS_MAX_FILE_ENTRY_EXTENTS \
+ OCFS_JOURNAL_FUZZ_CREDITS + \
OCFS_DEFAULT_DIR_NODE_SECTS)
+
+/* On very rare open operations (it's a first open and we're not in
+ * the open map), we have to change the file entry. */
+#define OCFS_OPEN_CREDITS 1
#endif /* _OCFSJOURNAL_H_ */
Modified: branches/nooin/src/inc/ocfs.h
===================================================================
--- branches/nooin/src/inc/ocfs.h 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/inc/ocfs.h 2004-04-16 01:28:18 UTC (rev 845)
@@ -229,71 +229,6 @@
#define ocfs_getpid() getpid()
#endif
-struct _ocfs_inode;
-
-/* OCFS2 Inode Private Data
- *
- * feoff/voteoff can change during rename. Luckily, rename takes a ton
- * of locks and does several checks, so you're safe reading these values
- * if any of the following is true:
- * 1) you have i_sem
- * 2) you have oin->main_res
- * 3) oin->open_hndl_cnt > 0
- */
-typedef struct _ocfs_inode_private
-{
- struct _ocfs_inode *oin;
- __u64 voteoff;
- __u64 feoff;
- atomic_t i_clean_buffer_seq;
- __u32 flags; /* see below */
-} ocfs_inode_private;
-
-/* has this inode been deleted, either from this node or from another node. */
-#define OCFS_INODE_DELETED 0x00000001
-/* is this the journal inode? */
-#define OCFS_INODE_JOURNAL 0x00000002
-
-#define GET_INODE_CLEAN_SEQ(i) (atomic_t *)(&(OCFS_GENERIC_IP(i)->i_clean_buffer_seq))
-
-#define OCFS_GENERIC_IP(i) ((ocfs_inode_private *)(i->u.generic_ip))
-
-#define inode_data_is_oin(i) (OCFS_GENERIC_IP(i)->oin != NULL)
-
-#define INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags & OCFS_INODE_DELETED)
-#define SET_INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags |= OCFS_INODE_DELETED)
-#define CLEAR_INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags &= (~OCFS_INODE_DELETED))
-
-#define INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags & OCFS_INODE_JOURNAL)
-#define SET_INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags |= OCFS_INODE_JOURNAL)
-#define CLEAR_INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags &= (~OCFS_INODE_JOURNAL))
-
-#define SET_INODE_VOTEOFF(i,o) \
-do { \
- OCFS_GENERIC_IP(i)->voteoff = o; \
-} while (0)
-
-#define GET_INODE_VOTEOFF(i) OCFS_GENERIC_IP(i)->voteoff
-
-#define SET_INODE_FEOFF(i,o) \
-do { \
- OCFS_GENERIC_IP(i)->feoff = o; \
-} while (0)
-
-#define GET_INODE_FEOFF(i) OCFS_GENERIC_IP(i)->feoff
-
-#define CLEAR_INODE_OIN(i) \
-do { \
- GET_INODE_OIN(i)= (void *)NULL; \
-} while (0)
-
-#define SET_INODE_OIN(i,o) \
-do { \
- GET_INODE_OIN(i)= (void *)o; \
-} while (0)
-
-#define GET_INODE_OIN(i) ((OCFS_GENERIC_IP(i)->oin))
-
#define FIRST_FILE_ENTRY(dir) ((char *) ((char *)dir)+OCFS_SECTOR_SIZE)
#define FILEENT(dir,idx) (ocfs_file_entry *) ( ((char *)dir) + \
((dir->index[idx]+1) * OCFS_SECTOR_SIZE))
@@ -1007,6 +942,7 @@
} while (0)
#endif
+#if 0
/* oin macros - currently the release is handled separately */
#ifdef OCFS_MEM_DBG
#define ocfs_allocate_oin() ((ocfs_inode *)({ \
@@ -1029,8 +965,8 @@
} \
oin; }))
#endif
+#endif
-
#define hashsize(n) ((__u32)1<<(n))
#define hashmask(n) (hashsize(n)-1)
@@ -1810,7 +1746,6 @@
bool cache_lock_held;
__u32 lock_state;
__u32 vote_state; /* Is the lockres being voted on over ipcdlm */
- ocfs_inode *oin;
spinlock_t lock_mutex;
wait_queue_head_t voted_event;
atomic_t voted_event_woken;
@@ -1831,7 +1766,6 @@
{
ocfs_obj_id obj_id;
struct inode *inode;
- struct _ocfs_super *osb; /* ocfs_inode belongs to this volume */
struct list_head recovery_list;
ocfs_sem main_res;
struct semaphore extend_sem;
@@ -1840,12 +1774,66 @@
ocfs_extent_map map;
__s64 alloc_size;
__u64 chng_seq_num;
- __u64 parent_dirnode_off; /* from the start of vol */
__u32 open_hndl_cnt;
__u32 oin_flags;
bool needs_verification;
};
+/* OCFS2 Inode Private Data
+ *
+ * feoff/voteoff can change during rename. Luckily, rename takes a ton
+ * of locks and does several checks, so you're safe reading these values
+ * if any of the following is true:
+ * 1) you have i_sem
+ * 2) you have oin->main_res
+ * 3) oin->open_hndl_cnt > 0
+ */
+typedef struct _ocfs_inode_private
+{
+ ocfs_inode oin;
+ __u64 voteoff;
+ __u64 feoff;
+ atomic_t i_clean_buffer_seq;
+ __u32 flags; /* see below */
+} ocfs_inode_private;
+
+/* has this inode been deleted, either from this node or from another node. */
+#define OCFS_INODE_DELETED 0x00000001
+/* is this the journal inode? */
+#define OCFS_INODE_JOURNAL 0x00000002
+
+#define GET_INODE_CLEAN_SEQ(i) (atomic_t *)(&(OCFS_GENERIC_IP(i)->i_clean_buffer_seq))
+
+#define OCFS_GENERIC_IP(i) ((ocfs_inode_private *)(i->u.generic_ip))
+
+#define INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags & OCFS_INODE_DELETED)
+#define SET_INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags |= OCFS_INODE_DELETED)
+#define CLEAR_INODE_DELETED(i) (OCFS_GENERIC_IP(i)->flags &= (~OCFS_INODE_DELETED))
+
+#define INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags & OCFS_INODE_JOURNAL)
+#define SET_INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags |= OCFS_INODE_JOURNAL)
+#define CLEAR_INODE_JOURNAL(i) (OCFS_GENERIC_IP(i)->flags &= (~OCFS_INODE_JOURNAL))
+
+#define SET_INODE_VOTEOFF(i,o) \
+do { \
+ OCFS_GENERIC_IP(i)->voteoff = o; \
+} while (0)
+
+#define GET_INODE_VOTEOFF(i) OCFS_GENERIC_IP(i)->voteoff
+
+#define SET_INODE_FEOFF(i,o) \
+do { \
+ OCFS_GENERIC_IP(i)->feoff = o; \
+} while (0)
+
+#define GET_INODE_FEOFF(i) OCFS_GENERIC_IP(i)->feoff
+
+/* callers of these next three functions should be fixed as we always
+ * have oin now. */
+#define inode_data_is_oin(i) (1)
+
+#define GET_INODE_OIN(i) (&(OCFS_GENERIC_IP(i)->oin))
+
typedef enum _ocfs_vol_state
{
VOLUME_DISABLED,
Modified: branches/nooin/src/inc/proto.h
===================================================================
--- branches/nooin/src/inc/proto.h 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/inc/proto.h 2004-04-16 01:28:18 UTC (rev 845)
@@ -44,7 +44,7 @@
int ocfs_acquire_lockres_ex (ocfs_lock_res * lockres, __u32 timeout);
void ocfs_release_lockres (ocfs_lock_res * lockres);
void ocfs_init_lockres (ocfs_super * osb, ocfs_lock_res * lockres, __u64 lock_id);
-int ocfs_create_update_lock (ocfs_super * osb, ocfs_inode * oin, __u64 lock_id, __u32 flags, bool new_file, struct inode *inode);
+int ocfs_create_update_lock (ocfs_super * osb, ocfs_inode * oin, __u64 lock_id, __u32 flags, bool new_file, struct inode *inode, ocfs_journal_handle *handle);
int ocfs_acquire_lock (ocfs_super * osb, __u64 lock_id, __u32 lock_type,
__u32 flags, ocfs_lock_res ** lr, struct buffer_head **bh, struct inode *inode);
int ocfs_release_lock (ocfs_super * osb, __u64 lock_id, __u32 lock_type, __u32 flags, ocfs_lock_res * lockres, struct buffer_head *bh, struct inode *inode);
@@ -57,7 +57,7 @@
void ocfs_extent_map_init (ocfs_extent_map * map);
void ocfs_extent_map_destroy (ocfs_extent_map * map);
-void ocfs_delete_all_extent_maps (ocfs_inode * oin);
+void ocfs_delete_all_extent_maps (ocfs_super * osb, ocfs_inode * oin);
void ocfs_remove_extent_map_entry (ocfs_super * osb, ocfs_extent_map * Map, __s64 Vbo, __u32 ByteCount);
bool ocfs_get_next_extent_map_entry (ocfs_super * osb, ocfs_extent_map * Map, __u32 RunIndex, __s64 * Vbo, __s64 * Lbo, __u32 * SectorCount);
bool ocfs_lookup_extent_map_entry (ocfs_super * osb, ocfs_extent_map * Map, __s64 Vbo, __s64 * Lbo, __u64 * SectorCount, __u32 * Index);
@@ -76,7 +76,7 @@
int ocfs_sync_file (struct file *file, struct dentry *dentry, int datasync);
ssize_t ocfs_file_write (struct file *filp, const char *buf, size_t count, loff_t * ppos);
ssize_t ocfs_file_read (struct file *filp, char *buf, size_t count, loff_t * ppos);
-int ocfs_extend_file (ocfs_super * osb, __u64 parent_off, ocfs_inode * oin, __u64 file_size, __u64 file_off, ocfs_journal_handle *passed_handle, struct inode *inode, struct iattr *attr);
+int ocfs_extend_file (ocfs_super * osb, ocfs_inode * oin, __u64 file_size, __u64 file_off, ocfs_journal_handle *passed_handle, struct inode *inode, struct iattr *attr);
int ocfs_setattr (struct dentry *dentry, struct iattr *attr);
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
int ocfs_getattr (struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat);
@@ -85,6 +85,7 @@
#endif
int ocfs_find_inode (struct inode *inode, unsigned long ino, void *opaque);
+int ocfs_inode_init_private(struct inode *inode);
void ocfs_populate_inode (struct inode *inode, ocfs_file_entry *fe, umode_t mode, void *genptr, bool create_ino);
void ocfs_read_locked_inode (struct inode *inode, ocfs_find_inode_args *args);
void ocfs_read_inode2 (struct inode *inode, void *opaque);
@@ -173,11 +174,11 @@
int ocfs_verify_update_oin (ocfs_super * osb, ocfs_inode * oin, int *needs_trunc);
-int ocfs_create_oin_from_entry (ocfs_super * osb, struct buffer_head * fe_bh, ocfs_inode ** new_oin, __u64 parent_dir_off, struct inode *inode);
-int ocfs_initialize_oin (ocfs_inode * oin, ocfs_super * osb, __u32 flags, __u64 file_off, __u64 lock_id, bool new_file, struct inode *inode);
-int ocfs_create_new_oin (ocfs_inode ** Returnedoin, __u64 alloc_size, ocfs_super * osb);
+int ocfs_inode_fill_ext_map(ocfs_super * osb, struct buffer_head * fe_bh, struct inode *inode);
+int ocfs_inode_open(ocfs_super *osb, struct buffer_head *fe_bh,
+ ocfs_journal_handle *handle, struct inode *inode);
int ocfs_create_root_oin (ocfs_super * osb, struct inode *root);
-void ocfs_release_oin (ocfs_inode * oin, bool FreeMemory);
+void ocfs_release_oin (ocfs_super *osb, ocfs_inode * oin, bool FreeMemory);
void ocfs_release_cached_oin (ocfs_super * osb, ocfs_inode * oin);
Modified: branches/nooin/src/inode.c
===================================================================
--- branches/nooin/src/inode.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/inode.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -28,6 +28,7 @@
#define OCFS_DEBUG_CONTEXT OCFS_DEBUG_CONTEXT_INODE
+extern struct semaphore recovery_list_sem;
static int ocfs_readpage (struct file *file, struct page *page);
static int ocfs_prepare_write (struct file *file, struct page *page, unsigned from, unsigned to);
@@ -170,7 +171,50 @@
} /* ocfs_find_inode */
#endif /* LINUX_VERSION_CODE < LinuxVersionCode(2,5,0) */
+/*
+ * ocfs_inode_init_private()
+ *
+ */
+int ocfs_inode_init_private(struct inode *inode)
+{
+ ocfs_inode_private *i = NULL;
+ struct _ocfs_inode *oin;
+ if (!inode)
+ BUG();
+
+ inode->u.generic_ip = kmem_cache_alloc(OcfsGlobalCtxt.inode_cache,
+ GFP_NOFS);
+
+ if (!inode->u.generic_ip)
+ return -ENOMEM;
+
+ i = (ocfs_inode_private *) inode->u.generic_ip;
+ oin = &i->oin;
+
+ memset(i, 0, sizeof(ocfs_inode_private));
+
+ i->flags = 0;
+ atomic_set(&i->i_clean_buffer_seq, 0);
+
+ /* Init OIN stuff. */
+ oin->obj_id.type = OCFS_TYPE_OIN;
+ oin->obj_id.size = sizeof (ocfs_inode);
+ ocfs_init_sem (&(oin->main_res));
+ init_MUTEX(&(oin->extend_sem));
+ OCFS_SET_FLAG (oin->oin_flags, OCFS_INITIALIZED_MAIN_RESOURCE);
+ oin->open_hndl_cnt = 0;
+ ocfs_extent_map_init (&oin->map);
+ INIT_LIST_HEAD(&oin->recovery_list);
+
+ /* These should be set in read_inode2. */
+ oin->alloc_size = 0ULL;
+ i->voteoff = 0ULL;
+ i->feoff = 0ULL;
+
+ return 0;
+} /* ocfs_inode_init_private */
+
/*
* ocfs_populate_inode()
*
@@ -181,6 +225,7 @@
ocfs_super *osb;
__u64 offset, fe_off;
unsigned long uniq_ino;
+ ocfs_inode *oin = NULL;
LOG_ENTRY_ARGS ("(0x%08x, %u, size:%u)\n", inode, mode, fe->file_size);
@@ -194,12 +239,10 @@
BUG();
}
- if (!inode->u.generic_ip)
- inode->u.generic_ip = kmem_cache_alloc(OcfsGlobalCtxt.inode_cache,
- GFP_NOFS);
- if (!inode->u.generic_ip) {
+ if (!inode->u.generic_ip && ocfs_inode_init_private(inode)) {
/* How can we recover gracefully? */
- LOG_ERROR_STR("unable to allocate private data for inode");
+ LOG_ERROR_STR("unable to allocate private data for "
+ "inode");
goto bail;
}
@@ -217,14 +260,17 @@
OCFS_SET_INODE_TIME(inode, i_atime, fe->modify_time);
OCFS_SET_INODE_TIME(inode, i_mtime, fe->modify_time);
OCFS_SET_INODE_TIME(inode, i_ctime, fe->create_time);
- if (genptr)
- SET_INODE_OIN(inode, genptr);
- else
- CLEAR_INODE_OIN(inode);
SET_INODE_VOTEOFF(inode, offset);
SET_INODE_FEOFF(inode, fe_off);
+ oin = GET_INODE_OIN(inode);
+ oin->alloc_size = fe->alloc_size;
+ oin->inode = inode;
+ oin->chng_seq_num = DISK_LOCK_SEQNUM (fe);
+ if (fe->attribs & OCFS_ATTRIB_DIRECTORY)
+ oin->oin_flags |= OCFS_OIN_DIRECTORY;
+
if (create_ino) {
uniq_ino = ocfs_inode_hash_insert(osb, offset, fe_off);
inode->i_ino = uniq_ino;
@@ -278,6 +324,8 @@
umode_t mode;
__u64 voteoff;
ocfs_file_entry *fe = NULL;
+ ocfs_inode *oin = NULL;
+ struct buffer_head *bh = NULL;
LOG_ENTRY_ARGS ("(%p, %p)\n", inode, args);
@@ -290,10 +338,7 @@
LOG_TRACE_ARGS("osb = %x\n", osb);
if (inode->i_ino == OCFS_ROOT_INODE_NUMBER) {
LOG_TRACE_ARGS("Populating root inode (i_ino = %lu)\n", inode->i_ino);
- if (!inode->u.generic_ip)
- inode->u.generic_ip = kmem_cache_alloc(
- OcfsGlobalCtxt.inode_cache, GFP_NOFS);
- if (!inode->u.generic_ip) {
+ if (!inode->u.generic_ip && ocfs_inode_init_private(inode)) {
/* How can we recover gracefully? */
LOG_ERROR_STR("unable to allocate private data for inode");
goto bail;
@@ -312,20 +357,41 @@
inode->i_fop = &ocfs_dops;
inode->i_uid = osb->vol_layout.uid;
inode->i_gid = osb->vol_layout.gid;
- SET_INODE_OIN (inode, osb->oin_root_dir);
SET_INODE_VOTEOFF(inode, osb->vol_layout.root_start_off);
SET_INODE_FEOFF(inode, 0);
+
+ oin = GET_INODE_OIN(inode);
+ oin->alloc_size = 0ULL;
+ oin->inode = inode;
+ oin->chng_seq_num = 0ULL;
+ oin->oin_flags |= OCFS_OIN_DIRECTORY | OCFS_OIN_ROOT_DIRECTORY;
+
ocfs_inode_hash_bind(osb, GET_INODE_VOTEOFF(inode), inode);
goto bail;
}
LOG_TRACE_ARGS("Populating non-root inode (i_ino = %lu)\n", inode->i_ino);
- if (args)
- fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(args->fe_bh);
- if (!fe) {
+
+ if (!args) {
make_bad_inode (inode);
goto bail;
}
+
+ /* Uhoh, they didn't give us a buffer. Read the FE off
+ * disk. This is safe because the kernel only does one
+ * read_inode2 for a new inode, and if it doesn't exist yet
+ * then nobody can be working on it! */
+ if (!args->fe_bh) {
+ status = ocfs_read_bh(osb, args->offset, &bh, 0, NULL);
+ if (status < 0) {
+ LOG_ERROR_STATUS(status);
+ make_bad_inode (inode);
+ goto bail;
+ }
+ } else
+ bh = args->fe_bh;
+
+ fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(bh);
newoin = NULL;
@@ -357,14 +423,18 @@
break;
}
ocfs_populate_inode (inode, fe, mode, newoin, false);
+
voteoff = S_ISDIR (mode) ? fe->extents[0].disk_off : fe->this_sector;
if (!args->skip_bind)
ocfs_inode_hash_bind(osb, voteoff, inode);
bail:
if (fe)
- OCFS_BH_PUT_DATA(args->fe_bh);
+ OCFS_BH_PUT_DATA(bh);
+ if (args && !args->fe_bh && bh)
+ brelse(bh);
+
LOG_EXIT ();
return;
} /* ocfs_read_locked_inode */
@@ -382,7 +452,7 @@
struct super_block *sb;
ocfs_find_inode_args *args = NULL;
ocfs_super *osb;
- ocfs_inode *newoin;
+ ocfs_inode *oin = NULL;
umode_t mode;
ocfs_file_entry *fe = NULL;
__u64 voteoff;
@@ -398,10 +468,7 @@
sb = inode->i_sb;
osb = (ocfs_super *) OCFS_GENERIC_SB_P(sb);
if (inode->i_ino == OCFS_ROOT_INODE_NUMBER) {
- if (!inode->u.generic_ip)
- inode->u.generic_ip = kmem_cache_alloc(
- OcfsGlobalCtxt.inode_cache, GFP_NOFS);
- if (!inode->u.generic_ip) {
+ if (!inode->u.generic_ip && ocfs_inode_init_private(inode)) {
/* How can we recover gracefully? */
LOG_ERROR_STR("unable to allocate private data for inode");
goto bail;
@@ -423,9 +490,15 @@
inode->i_fop = &ocfs_dops;
inode->i_uid = osb->vol_layout.uid;
inode->i_gid = osb->vol_layout.gid;
- SET_INODE_OIN (inode, osb->oin_root_dir);
SET_INODE_VOTEOFF(inode, osb->vol_layout.root_start_off);
SET_INODE_FEOFF(inode, 0);
+
+ oin = GET_INODE_OIN(inode);
+ oin->alloc_size = 0ULL;
+ oin->inode = inode;
+ oin->chng_seq_num = 0ULL;
+ oin->oin_flags |= OCFS_OIN_DIRECTORY | OCFS_OIN_ROOT_DIRECTORY;
+
ocfs_inode_hash_bind(osb, GET_INODE_VOTEOFF(inode), inode);
goto bail;
}
@@ -436,7 +509,6 @@
}
args = (ocfs_find_inode_args *) opaque;
- newoin = NULL;
/* Uhoh, they didn't give us a buffer. Read the FE off
* disk. This is safe because the kernel only does one
@@ -482,7 +554,7 @@
mode |= S_IFREG;
break;
}
- ocfs_populate_inode (inode, fe, mode, newoin, false);
+ ocfs_populate_inode (inode, fe, mode, NULL, false);
voteoff = S_ISDIR (mode) ? fe->extents[0].disk_off : fe->this_sector;
if (!args->skip_bind)
@@ -541,27 +613,11 @@
goto bail;
args = (ocfs_find_inode_args *) opaque;
- if (!ocfs_linux_get_inode_offset (inode, &fileOff, NULL)) {
- LOG_TRACE_STR ("could not get inode offset");
+ if (GET_INODE_FEOFF(inode) != args->offset) {
+ LOG_ERROR_STATUS(-EINVAL);
goto bail;
}
- if (S_ISDIR (inode->i_mode)) {
- LOG_TRACE_STR ("find_actor -> S_ISDIR\n");
- fe = OCFS_BH_GET_DATA_READ(args->fe_bh); /* read */
- if (fe->extents[0].disk_off != fileOff) {
- LOG_TRACE_ARGS
- ("DIR : inode number same but full offset does not match: %u.%u != %u.%u\n",
- fe->extents[0].disk_off, fileOff);
- goto bail;
- }
- } else if (args->offset != fileOff) {
- LOG_TRACE_ARGS
- ("FILE : inode number same but full offset does not match: %u.%u != %u.%u\n",
- args->offset, fileOff);
- goto bail;
- }
-
ret = 1;
bail:
if (fe)
@@ -660,17 +716,6 @@
if (inode_data_is_oin(inode))
oin = GET_INODE_OIN(inode);
- /* can we destroy the oin? Uhm, shouldn't this be a test
- * against a count of '3'? */
- if (oin && (atomic_read (&inode->i_count) == 2) &&
- (inode->i_ino != OCFS_ROOT_INODE_NUMBER)) {
- ocfs_extent_map_destroy (&oin->map);
- ocfs_extent_map_init (&oin->map);
- ocfs_release_cached_oin (osb, oin);
- ocfs_release_oin (oin, true);
- oin = NULL;
- }
-
/* Ok, if after this iput we would be the last holder of the
* root inode, then we know we're unmounting so just dump it
* now. */
@@ -717,6 +762,12 @@
if (!inode)
goto bail;
+ LOG_TRACE_ARGS("Clearing inode %u (voteoff: %u.%u, "
+ "feoff: %u.%u)\n", inode->i_ino,
+ HILO(GET_INODE_VOTEOFF(inode)),
+ HILO(GET_INODE_FEOFF(inode)));
+
+ /* we should not really be using osb in this context. */
osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
if (!ocfs_linux_get_inode_offset(inode, &offset, NULL)) {
@@ -727,42 +778,63 @@
/* offset == 0 if this inode is newly created and hasn't been
* filled in yet. */
- if (offset == 0)
+ if (offset == 0) {
+ LOG_ERROR_STR("uhm, feoff = 0!");
goto bail;
+ }
- if (inode_data_is_oin (inode)) {
- LOG_TRACE_STR ("inode with oin : clear inode");
+ oin = GET_INODE_OIN(inode);
- oin = GET_INODE_OIN(inode);
- if (oin != osb->oin_root_dir)
- BUG();
-
+ if (inode->i_ino == OCFS_ROOT_INODE_NUMBER) {
LOG_TRACE_STR("this is the root inode, doing cleanup now!");
ocfs_sync_blockdev(inode->i_sb);
LOG_TRACE_STR ("syncing past root inode");
LOG_TRACE_STR ("calling dismount");
ocfs_dismount_volume (inode->i_sb);
+ goto bail;
+ }
+
+ OCFS_SET_FLAG (oin->oin_flags, OCFS_OIN_IN_TEARDOWN);
+
+ lockres = oin->lock_res;
+ if (lockres) {
+ ocfs_acquire_lockres (lockres);
+ ocfs_release_lockres (lockres);
+ oin->lock_res = NULL;
+ ocfs_put_lockres (lockres);
+ lockres = NULL;
+ }
+
+ ocfs_extent_map_destroy (&oin->map);
+ ocfs_extent_map_init (&oin->map);
+
+ down(&recovery_list_sem);
+ list_del(&oin->recovery_list);
+ up(&recovery_list_sem);
+
+ ocfs_del_sem (&(oin->main_res));
+ OCFS_CLEAR_FLAG (oin->oin_flags, OCFS_INITIALIZED_MAIN_RESOURCE);
+
+ /* clean out the oin ... why?! */
+ memset(oin, 0, sizeof(ocfs_inode));
+
+ if (!ocfs_lookup_sector_node (osb, offset, &lockres)) {
+ if (lockres) {
+ ocfs_remove_sector_node (osb, lockres);
+ ocfs_put_lockres(lockres);
+ } else
+ LOG_TRACE_STR ("lockres in hash is null");
} else {
- if (!ocfs_lookup_sector_node (osb, offset, &lockres)) {
- if (lockres) {
- if (lockres->oin) {
- ocfs_put_lockres (lockres->oin->lock_res);
- lockres->oin->lock_res = NULL;
- lockres->oin = NULL;
- }
- ocfs_remove_sector_node (osb, lockres);
- ocfs_put_lockres(lockres);
- } else
- LOG_TRACE_STR ("lockres in hash is null");
- } else {
- LOG_TRACE_STR("hashtable has already been destroyed.");
- }
+ LOG_TRACE_STR("hashtable has already been destroyed.");
}
- if (inode->u.generic_ip)
+bail:
+ if (inode && inode->u.generic_ip) {
kmem_cache_free(OcfsGlobalCtxt.inode_cache,
inode->u.generic_ip);
-bail:
+ inode->u.generic_ip = NULL;
+ }
+
LOG_EXIT ();
return;
} /* ocfs_clear_inode */
@@ -860,7 +932,7 @@
if (unlock)
ocfs_up_sem (&(oin->main_res));
- status = ocfs_extend_file (osb, oin->parent_dirnode_off, oin, newsize, GET_INODE_FEOFF(inode), NULL, inode, NULL);
+ status = ocfs_extend_file (osb, oin, newsize, GET_INODE_FEOFF(inode), NULL, inode, NULL);
if (unlock)
ocfs_down_sem (&(oin->main_res), true);
@@ -976,7 +1048,7 @@
goto bail;
}
- osb = (ocfs_super *) oin->osb;
+ osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
vbo = (__s64) iblock << inode->i_sb->s_blocksize_bits;
if (!INODE_JOURNAL(inode) && vbo >= oin->alloc_size) {
@@ -1114,7 +1186,7 @@
}
oin = GET_INODE_OIN(inode);
- osb = (ocfs_super *) oin->osb;
+ osb = (ocfs_super *) OCFS_GENERIC_SB_P(inode->i_sb);
vbo = (__s64) iblock << inode->i_sb->s_blocksize_bits;
len = 1;
Modified: branches/nooin/src/journal.c
===================================================================
--- branches/nooin/src/journal.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/journal.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -940,10 +940,16 @@
OCFS_BH_PUT_DATA(bh);
fe = NULL;
- status = ocfs_create_new_oin(&oin, alloc_size, osb);
- status = ocfs_initialize_oin(oin, osb, 0, lock_id, lock_id, false, NULL);
+ /* we just changed this but extend_system_file doesn't know
+ * about oins, so we update alloc_size ourselves. */
+ oin = GET_INODE_OIN(inode);
+ oin->alloc_size = alloc_size;
+ status = ocfs_create_update_lock(osb, oin, lock_id, 0, false, inode, NULL);
+ if (status < 0) {
+ LOG_ERROR_STATUS(status);
+ goto done;
+ }
oin->open_hndl_cnt++;
- SET_INODE_OIN(inode, oin);
LOG_TRACE_ARGS("oin->alloc_size = %u.%u\n", HI(oin->alloc_size),
LO(oin->alloc_size));
@@ -1050,9 +1056,7 @@
/* release the oin here. Isn't this racy? */
if (inode_data_is_oin(inode)) {
oin = GET_INODE_OIN(inode);
- CLEAR_INODE_OIN(inode);
oin->open_hndl_cnt--;
- ocfs_release_oin(oin, true);
}
/* unlock our journal */
@@ -1570,14 +1574,13 @@
fe = NULL;
- status = ocfs_create_new_oin(&oin, alloc_size, osb);
+ oin = GET_INODE_OIN(inode);
+ oin->alloc_size = alloc_size;
+ status = ocfs_create_update_lock(osb, oin, lock_id, 0, false, inode, NULL);
if (status < 0) {
LOG_ERROR_STATUS(status);
goto done;
}
- status = ocfs_initialize_oin(oin, osb, 0, lock_id, lock_id, false,
- NULL);
- SET_INODE_OIN(inode, oin);
status = ocfs_force_read_journal(osb, inode->i_size, oin, inode);
if (status < 0) {
@@ -1635,14 +1638,7 @@
CLEAR_NODE_IN_RECOVERY(osb, node_num);
ocfs_recover_oin_locks(osb, node_num);
done:
- /* close the journal file */
if (inode)
- CLEAR_INODE_OIN(inode);
-
- if (oin)
- ocfs_release_oin(oin, true);
-
- if (inode)
iput(inode);
if (recovery_lock)
Modified: branches/nooin/src/namei.c
===================================================================
--- branches/nooin/src/namei.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/namei.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -196,8 +196,7 @@
goto leave;
}
- inode->u.generic_ip = kmem_cache_alloc(OcfsGlobalCtxt.inode_cache, GFP_NOFS);
- if (!inode->u.generic_ip) {
+ if (ocfs_inode_init_private(inode)) {
LOG_ERROR_STATUS(status = -ENOMEM);
goto leave;
}
@@ -244,24 +243,12 @@
goto leave;
}
- status = ocfs_create_new_oin (&oin, 0ULL, osb);
- if (status < 0) {
- LOG_ERROR_STATUS (status);
- goto leave;
- }
-
fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(new_fe_bh); /* read */
file_off = fe->this_sector;
dirnode_off = fe->extents[0].disk_off;
- oinflags = OCFS_OIN_CACHE_UPDATE | (S_ISDIR (mode) ? OCFS_OIN_DIRECTORY : 0);
+ oinflags = (S_ISDIR (mode) ? OCFS_OIN_DIRECTORY : 0);
- OCFS_BH_PUT_DATA(new_fe_bh);
- fe = NULL;
-
- status = ocfs_initialize_oin (oin, osb, oinflags, file_off,
- S_ISDIR (mode) ? dirnode_off : file_off, true, inode);
-
if (!ocfs_linux_get_inode_offset (dir, &parent_off, &ParentOin)) {
LOG_ERROR_STATUS (status = -ENOENT);
goto leave;
@@ -270,8 +257,24 @@
if (ParentOin)
OCFS_CLEAR_FLAG (ParentOin->oin_flags, OCFS_OIN_IN_USE);
+ ocfs_populate_inode (inode, fe, mode, NULL, true);
+ insert_inode_hash (inode);
+ ocfs_inode_hash_bind(osb, GET_INODE_VOTEOFF(inode), inode);
+
+ handle->new_file_lockid = fe->this_sector;
+ OCFS_BH_PUT_DATA(new_fe_bh);
+ fe = NULL;
+
+ oin = GET_INODE_OIN(inode);
+ status = ocfs_create_update_lock(osb, oin, GET_INODE_VOTEOFF(inode),
+ oinflags, true, inode, handle);
+ if (status < 0)
+ LOG_ERROR_STATUS(status);
+
fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(new_fe_bh); /* read */
+ /* Insert the OFile on the OIN list */
+ oin->chng_seq_num = DISK_LOCK_SEQNUM (fe);
if (oin->lock_res != NULL) {
ocfs_lock_res *lockres = oin->lock_res;
ocfs_acquire_lockres(lockres);
@@ -286,28 +289,15 @@
}
ocfs_release_lockres(lockres);
}
-
- /* Insert the OFile on the OIN list */
- oin->chng_seq_num = DISK_LOCK_SEQNUM (fe);
- oin->parent_dirnode_off = parent_off;
-
- LOG_TRACE_ARGS("ocfs_mknod: new_fe_bh: this_sector = %u.%u, "
- "extents[0].disk_off = %u.%u\n",
- HILO(fe->this_sector), HILO(fe->extents[0].disk_off));
-
- if (ocfs_inc_icount(inode) < 0)
- BUG();
- oin->inode = inode;
-
- ocfs_populate_inode (inode, fe, mode, oin, true);
- insert_inode_hash (inode);
- ocfs_inode_hash_bind(osb, GET_INODE_VOTEOFF(inode), inode);
- d_instantiate (dentry, inode);
-
- handle->new_file_lockid = fe->this_sector;
OCFS_BH_PUT_DATA(new_fe_bh);
fe = NULL;
+ LOG_TRACE_ARGS("ocfs2: Created inode %u (voteoff: %u.%u, "
+ "feoff: %u.%u)\n", inode->i_ino,
+ HILO(GET_INODE_VOTEOFF(inode)),
+ HILO(GET_INODE_FEOFF(inode)));
+
+ d_instantiate (dentry, inode);
ocfs_commit_trans(handle);
status = 0;
@@ -589,15 +579,6 @@
__u64 parentOff, fileOff;
bool do_release = false;
struct inode *parentInode = dentry->d_parent->d_inode;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
- /*
- * On a 2.6 kernel sys_unlink will increment the inode
- * count before calling the filesystem unlink function
- */
- int max_cnt = 3; /* one for this process, inode hash, and sys_unlink */
-#else
- int max_cnt = 2; /* one for this process and one for inode hash */
-#endif
LOG_ENTRY_ARGS ("(0x%08x, 0x%08x, '%*s')\n", dir, dentry,
dentry->d_name.len, dentry->d_name.name);
@@ -615,13 +596,6 @@
status = -EBUSY;
- if (oin && oin->inode)
- max_cnt++;
-
-// removed this check as technically i don't even think it's legal.
-// if (atomic_read (&inode->i_count) > max_cnt || atomic_read (&dentry->d_count) > 2) {
-// LOG_ERROR_ARGS ("i_count > %d or d_count > 2\n", max_cnt);
-// } else if (!ocfs_empty(dentry)) {
if (!ocfs_empty(dentry)) {
LOG_TRACE_STR ("dentry is not empty, cannot delete");
} else if (oin && oin->open_hndl_cnt > 0) {
@@ -672,17 +646,12 @@
}
goto bail;
}
-
- if (oin)
- ocfs_release_cached_oin (osb, oin);
}
if (do_release)
{
- if (oin)
- ocfs_release_oin (oin, true);
- else {
- if (fileOff != -1) {
+ if (!oin) {
+ if (fileOff != -1) {
tmpstat = ocfs_lookup_sector_node (osb, fileOff, &lockres);
if (tmpstat >= 0 && lockres) {
ocfs_remove_sector_node (osb, lockres);
@@ -939,7 +908,6 @@
__u32 newfe_flags = 0;
__u32 newfe_lockid = 0;
int needs_trunc = 0;
- int max_cnt = 2;
LOG_ENTRY_ARGS ("(0x%08x, 0x%08x, 0x%08x, 0x%08x, from='%*s' to='%*s')\n",
old_dir, old_dentry, new_dir, new_dentry,
@@ -970,13 +938,6 @@
BUG();
}
- if (oldOIN && oldOIN->inode)
- max_cnt++;
-
-// if (atomic_read (&old_inode->i_count) > max_cnt) {
-// status = -EBUSY;
-// goto bail;
-// } else
if (atomic_read (&old_dentry->d_count) > 2) {
shrink_dcache_parent (old_dentry);
if (atomic_read (&old_dentry->d_count) > 2) {
@@ -1263,18 +1224,8 @@
LOG_ERROR_STATUS(status);
}
- if (oldOIN) {
- ocfs_release_cached_oin (osb, oldOIN);
- ocfs_release_oin (oldOIN, true);
- if (new_dentry->d_inode)
+ if (oldOIN && new_dentry->d_inode)
fsync_inode_buffers(old_dentry->d_inode);
- }
-
- /* delete the targets oin here as we've just blown it away! */
- if (kill_newfe && newOIN && delete_target_oin) {
- ocfs_release_cached_oin (osb, newOIN);
- ocfs_release_oin (newOIN, true);
- }
}
old_inode->i_nlink++;
@@ -1371,8 +1322,7 @@
goto bail;
}
- inode->u.generic_ip = kmem_cache_alloc(OcfsGlobalCtxt.inode_cache, GFP_NOFS);
- if (!inode->u.generic_ip) {
+ if (ocfs_inode_init_private(inode)) {
LOG_ERROR_STATUS(status = -ENOMEM);
goto bail;
}
@@ -1426,7 +1376,7 @@
OCFS_BH_PUT_DATA(new_fe_bh);
fe = NULL;
- status = ocfs_extend_file (osb, parent_off, NULL, newsize, file_off, handle, inode, NULL);
+ status = ocfs_extend_file (osb, NULL, newsize, file_off, handle, inode, NULL);
if (status < 0) {
if (status != -ENOSPC && status != -EINTR) {
LOG_ERROR_ARGS ("Failed to extend file to %u.%u", HILO (newsize));
@@ -1435,20 +1385,8 @@
}
goto abort_trans;
}
-
- status = ocfs_create_oin_from_entry(osb, new_fe_bh, &oin,
- parent_off, NULL);
- if (status < 0) {
- LOG_ERROR_STATUS(status);
- goto abort_trans;
- }
-
inode->i_rdev = OCFS_NODEV;
- if (ocfs_inc_icount(inode) < 0)
- BUG();
- oin->inode = inode;
-
fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(new_fe_bh); /* read */
ocfs_populate_inode (inode, fe, S_IFLNK | S_IRWXUGO, oin, true);
OCFS_BH_PUT_DATA(new_fe_bh);
@@ -1456,6 +1394,19 @@
inode->i_size = newsize;
inode->i_blocks = (newsize + sb->s_blocksize) >> sb->s_blocksize_bits;
+
+ status = ocfs_inode_open(osb, new_fe_bh, handle, inode);
+ if (status < 0) {
+ LOG_ERROR_STATUS(status);
+ goto abort_trans;
+ }
+
+ status = ocfs_inode_fill_ext_map(osb, new_fe_bh, inode);
+ if (status < 0) {
+ LOG_ERROR_STATUS(status);
+ goto abort_trans;
+ }
+
insert_inode_hash (inode);
ocfs_inode_hash_bind(osb, GET_INODE_VOTEOFF(inode), inode);
d_instantiate (dentry, inode);
@@ -1489,6 +1440,7 @@
if (status < 0)
ocfs_bh_sem_hash_cleanup_pid(ocfs_getpid());
+
LOG_EXIT_STATUS (status);
return status;
} /* ocfs_symlink */
@@ -1869,8 +1821,11 @@
if (inode && status == 0 && !(flags & FLAG_DEL_INODE)) {
SET_INODE_DELETED(inode);
- LOG_TRACE_ARGS("removing inode %lu, voteoff = %u.%u\n",
- inode->i_ino, HILO(GET_INODE_VOTEOFF(inode)));
+// printk("ocfs2: removing inode (%p, %p) %lu, voteoff = %u.%u, "
+// "feoff = %u.%u\n", inode, inode->u.generic_ip,
+// inode->i_ino,
+// HILO(GET_INODE_VOTEOFF(inode)),
+// HILO(GET_INODE_FEOFF(inode)));
ocfs_inode_hash_remove(&osb->inode_hash,
GET_INODE_VOTEOFF(inode));
}
Modified: branches/nooin/src/nm.c
===================================================================
--- branches/nooin/src/nm.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/nm.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -31,8 +31,9 @@
/* for lack of a better name... protects oin->num_extends. */
spinlock_t oin_num_ext_lock = SPIN_LOCK_UNLOCKED;
+struct semaphore recovery_list_sem;
-static inline int get_process_vote_action(ocfs_super * osb, ocfs_lock_res *lockres, __u32 node_num, __u32 flags, int status, bool *master_alive, ocfs_inode **oin);
+static inline int get_process_vote_action(ocfs_super * osb, ocfs_lock_res *lockres, __u32 node_num, __u32 flags, int status, bool *master_alive, ocfs_inode **oin, struct inode *inode);
static int ocfs_disk_update_resource (ocfs_super * osb, ocfs_lock_res * lock_res, struct buffer_head **bh, __u32 timeout, struct inode *inode);
static int ocfs_search_commited(ocfs_super *osb, ocfs_lock_res *lockres);
static int ocfs_schedule_process_vote(ocfs_super *osb, struct buffer_head *bh, int vote_node);
@@ -640,7 +641,7 @@
} /* ocfs_find_update_res */
static inline int get_process_vote_action(ocfs_super * osb, ocfs_lock_res *lockres, __u32 node_num,
- __u32 flags, int status, bool *master_alive, ocfs_inode **oin)
+ __u32 flags, int status, bool *master_alive, ocfs_inode **oin, struct inode *inode)
{
int vote_type = INVALID_REQUEST;
bool my_node_wins = false;
@@ -650,6 +651,9 @@
HILO(lockid), node_num, flags);
*oin = NULL;
+ if (inode)
+ *oin = GET_INODE_OIN(inode);
+
*master_alive = true;
if (status < 0) {
if (status == -ETIMEDOUT) {
@@ -662,8 +666,6 @@
lockres->master_node_num, OCFS_MAXIMUM_NODES);
my_node_wins = lockres->vote_state & LOCK_STATE_IN_VOTING &&
node_num < osb->node_num;
- if (lockres->oin)
- *oin = lockres->oin;
}
if (flags & FLAG_DROP_READONLY) {
@@ -863,7 +865,7 @@
}
vote_type = get_process_vote_action(osb, lockres, node_num, flags,
- status, &master_alive, &oin);
+ status, &master_alive, &oin, inode);
#ifdef VERBOSE_PROCESS_VOTE
printk("(%u) ocfs_process_vote: %s request for lockid: %u.%u, fe_off: %u.%u, action: (%u) %s, type: %s\n", ocfs_getpid(),
@@ -950,7 +952,6 @@
case DELETE_RENAME:
LOG_TRACE_STR("DELETE_RENAME");
- oin = lockres->oin;
/* all cases except open_hndl_cnt > 0 will vote YES */
vote_response = FLAG_VOTE_NODE;
@@ -974,9 +975,6 @@
ocfs_down_sem (oin_sem, true);
}
- /* make sure that lockres->oin has not changed */
- oin = lockres->oin;
-
if (oin && oin->open_hndl_cnt > 0) {
/* the NO vote for delete/rename */
vote_response = FLAG_VOTE_OIN_ALREADY_INUSE;
@@ -1312,17 +1310,12 @@
if (flags & (FLAG_FILE_EXTEND|FLAG_FILE_TRUNCATE) &&
((flags & FLAG_ACQUIRE_LOCK && vote_response==FLAG_VOTE_NODE) ||
(flags & FLAG_RELEASE_LOCK))) {
- oin = NULL;
- if (lockres && lockres->oin)
- oin = lockres->oin;
-
+
LOG_TRACE_ARGS("responding YES to %s %s request, oin=%p, node=%u\n", flags & FLAG_FILE_EXTEND ?
"extend" : "truncate", flags & FLAG_RELEASE_LOCK ?
"release" : "acquire", oin, node_num);
if (oin && (flags & FLAG_ACQUIRE_LOCK)) {
- ocfs_down_sem (&(osb->osb_res), true);
-
spin_lock(&oin_num_ext_lock);
if (oin->num_extends < 0)
@@ -1333,7 +1326,6 @@
spin_unlock(&oin_num_ext_lock);
} else {
spin_unlock(&oin_num_ext_lock);
- ocfs_up_sem (&(osb->osb_res));
/* take the extend_sem on behalf of
* this other node. It won't be
@@ -1344,15 +1336,15 @@
* inode. */
down(&oin->extend_sem);
- ocfs_down_sem (&(osb->osb_res), true);
+ down(&recovery_list_sem);
spin_lock(&oin_num_ext_lock);
oin->num_extends++;
list_add_tail(&oin->recovery_list, &osb->lock_recovery_lists[node_num]);
spin_unlock(&oin_num_ext_lock);
+ up(&recovery_list_sem);
}
- ocfs_up_sem (&(osb->osb_res));
} else if (oin && (flags & FLAG_RELEASE_LOCK)) {
- ocfs_down_sem (&(osb->osb_res), true);
+ down(&recovery_list_sem);
spin_lock(&oin_num_ext_lock);
oin->num_extends--;
@@ -1366,7 +1358,7 @@
}
spin_unlock(&oin_num_ext_lock);
- ocfs_up_sem (&(osb->osb_res));
+ up(&recovery_list_sem);
}
}
@@ -1461,7 +1453,7 @@
LOG_ENTRY_ARGS("(node_num = %u)\n", node_num);
- ocfs_down_sem (&(osb->osb_res), true);
+ down(&recovery_list_sem);
list_for_each_safe (iter, temp, &osb->lock_recovery_lists[node_num]) {
oin = list_entry (iter, ocfs_inode, recovery_list);
if (oin->obj_id.type != OCFS_TYPE_OIN) {
@@ -1474,6 +1466,7 @@
if (oin->num_extends) {
oin->num_extends = 0;
list_del(&oin->recovery_list);
+ INIT_LIST_HEAD(&oin->recovery_list);
up(&oin->extend_sem);
} else
LOG_ERROR_STR("oin is in recovery list, but has zero extend counter value!");
@@ -1481,7 +1474,7 @@
spin_unlock(&oin_num_ext_lock);
}
- ocfs_up_sem (&(osb->osb_res));
+ up (&recovery_list_sem);
LOG_EXIT();
}
Modified: branches/nooin/src/oin.c
===================================================================
--- branches/nooin/src/oin.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/oin.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -269,15 +269,83 @@
return status;
} /* ocfs_verify_update_oin */
+/* you should be holding i_sem and main_res in this function.
+ *
+ * Put a lockres on the oin and if needed add ourselves to the open
+ * map. Only call this on 1st open of a file. Marks the oin as "in use"
+ */
+int ocfs_inode_open(ocfs_super *osb, struct buffer_head *fe_bh,
+ ocfs_journal_handle *handle, struct inode *inode)
+{
+ int status = 0;
+ ocfs_inode *oin;
+ ocfs_file_entry *fe = NULL;
+ bool local_handle = true;
+ __u32 flags = OCFS_OIN_IN_USE;
+ LOG_ENTRY ();
+
+ if (handle)
+ local_handle = false;
+
+ oin = GET_INODE_OIN(inode);
+
+ fe = (ocfs_file_entry *) OCFS_BH_GET_DATA_READ(fe_bh); /* read */
+
+ /* why do we update these here? */
+ oin->alloc_size = fe->alloc_size;
+ oin->chng_seq_num = DISK_LOCK_SEQNUM (fe);
+ if (fe->this_sector == 0)
+ LOG_ERROR_STR ("this_sector=0");
+
+ OCFS_BH_PUT_DATA(fe_bh);
+
+ flags |= oin->oin_flags;
+
+ if (!(flags & OCFS_OIN_ROOT_DIRECTORY)) {
+ if (local_handle) {
+ handle = ocfs_start_trans(osb, OCFS_OPEN_CREDITS);
+ if (!handle) {
+ LOG_ERROR_STATUS(status = -ENOMEM);
+ goto leave;
+ }
+ /* we want this to be a really fast transaction. */
+ ocfs_handle_set_sync(handle, false);
+ ocfs_handle_set_checkpoint(handle, false);
+ }
+
+ status = ocfs_create_update_lock(osb, oin,
+ GET_INODE_VOTEOFF(inode),
+ flags, false, inode, handle);
+ if (status < 0) {
+ if (status != -EINTR)
+ LOG_ERROR_STATUS (status);
+ goto leave;
+ }
+ }
+ oin->oin_flags |= OCFS_OIN_IN_USE;
+
+leave:
+ if (local_handle && handle) {
+ if (status < 0)
+ ocfs_abort_trans(handle);
+ else
+ ocfs_commit_trans(handle);
+ }
+
+ LOG_EXIT_STATUS (status);
+ return status;
+}
+
+
+
/* ocfs_create_oin_from_entry()
*
*/
-int ocfs_create_oin_from_entry (ocfs_super * osb, struct buffer_head * fe_bh, ocfs_inode ** new_oin, __u64 parent_dir_off, struct inode *inode)
+int ocfs_inode_fill_ext_map(ocfs_super * osb, struct buffer_head * fe_bh, struct inode *inode)
{
int status = 0;
ocfs_inode *oin;
- __u64 lockId;
int j;
__s64 tempVbo;
__s64 tempLbo;
@@ -291,7 +359,7 @@
LOG_ENTRY ();
- *new_oin = NULL;
+ oin = GET_INODE_OIN(inode);
/* get a copy of fe, used readonly in this path and */
/* ocfs_create_new_oin will deadlock if fe_bh is locked */
@@ -303,134 +371,92 @@
tmp = OCFS_BH_GET_DATA_READ(fe_bh); /* read */
memcpy(fe, tmp, sizeof(ocfs_file_entry));
OCFS_BH_PUT_DATA(fe_bh);
+ tempoff = fe->this_sector;
- /* We have a new file on disk , so create an oin for the file */
- status = ocfs_create_new_oin (&oin, fe->alloc_size, osb);
- if (status < 0) {
- LOG_ERROR_STATUS (status);
+ /* we don't want to do the extent map stuff for a directory. */
+ if (fe->attribs & OCFS_ATTRIB_DIRECTORY)
goto leave;
- }
- oin->parent_dirnode_off = parent_dir_off;
- oin->chng_seq_num = DISK_LOCK_SEQNUM (fe);
-
- if (fe->this_sector == 0)
- LOG_ERROR_STR ("this_sector=0");
-
- tempoff = fe->this_sector;
-
- /* The oins gets Linked into the osb in this function */
-
- if (fe->attribs & OCFS_ATTRIB_DIRECTORY) {
- lockId = fe->extents[0].disk_off;
-
- status = ocfs_initialize_oin (oin, osb,
- OCFS_OIN_DIRECTORY | OCFS_OIN_IN_USE,
- tempoff, lockId, false, inode);
- if (status < 0) {
- if (status != -EINTR)
- LOG_ERROR_STATUS (status);
- goto leave;
+ if (fe->local_ext) {
+ for (j = 0; j < fe->next_free_ext; j++) {
+ tempVbo = fe->extents[j].file_off;
+ tempLbo = fe->extents[j].disk_off;
+ tempSize = fe->extents[j].num_bytes;
+
+ /* Add the Extent to extent map */
+ bRet = ocfs_add_extent_map_entry (osb,
+ &oin->map,
+ tempVbo,
+ tempLbo,
+ tempSize);
+ if (!bRet) {
+ LOG_ERROR_STATUS (status = -ENOMEM);
+ goto leave;
+ }
}
} else {
- __u32 flags = OCFS_OIN_IN_USE;
-
- if((DISK_LOCK_FILE_LOCK(fe) == OCFS_DLM_ENABLE_CACHE_LOCK)
- && (DISK_LOCK_CURRENT_MASTER(fe) == osb->node_num))
- flags |= OCFS_OIN_CACHE_UPDATE;
- status = ocfs_initialize_oin (oin, osb, flags,
- tempoff, tempoff, false, inode);
+ __u64 next_data_ext;
+
+ /* Extents are branched and we are no longer using */
+ /* Local Extents for this File Entry. */
+
+ status = ocfs_get_leaf_extent (osb, fe, 0, &extent_bh, inode);
if (status < 0) {
- if (status != -EINTR)
- LOG_ERROR_STATUS (status);
+ LOG_ERROR_STATUS (status);
goto leave;
}
-
- if (fe->local_ext) {
- for (j = 0; j < fe->next_free_ext; j++) {
- tempVbo = fe->extents[j].file_off;
- tempLbo = fe->extents[j].disk_off;
- tempSize = fe->extents[j].num_bytes;
-
+
+ while (1) {
+ extent = (ocfs_extent_group *) OCFS_BH_GET_DATA_READ(extent_bh); /* read */
+
+ if (!IS_VALID_EXTENT_DATA (extent)) {
+ LOG_ERROR_STATUS(status = -EFAIL);
+ goto leave;
+ }
+
+ for (j = 0; j < extent->next_free_ext; j++) {
+ tempVbo = extent->extents[j].file_off;
+ tempLbo = extent->extents[j].disk_off;
+ tempSize = extent->extents[j].num_bytes;
+
/* Add the Extent to extent map */
- bRet = ocfs_add_extent_map_entry (osb,
- &oin->map,
- tempVbo,
- tempLbo,
- tempSize);
+ bRet =
+ ocfs_add_extent_map_entry (osb,
+ &oin->map,
+ tempVbo,
+ tempLbo,
+ tempSize);
if (!bRet) {
- LOG_ERROR_STATUS (status = -ENOMEM);
+ LOG_ERROR_STATUS (status =
+ -ENOMEM);
goto leave;
}
}
- } else {
- __u64 next_data_ext;
-
- /* Extents are branched and we are no longer using */
- /* Local Extents for this File Entry. */
-
- status = ocfs_get_leaf_extent (osb, fe, 0, &extent_bh, inode);
- if (status < 0) {
- LOG_ERROR_STATUS (status);
- goto leave;
- }
-
- while (1) {
- extent = (ocfs_extent_group *) OCFS_BH_GET_DATA_READ(extent_bh); /* read */
-
- if (!IS_VALID_EXTENT_DATA (extent)) {
- LOG_ERROR_STATUS(status = -EFAIL);
+
+ if (extent->next_data_ext > 0) {
+ if (!extent->next_data_ext) {
+ LOG_ERROR_STATUS (status = -EFAIL);
goto leave;
}
+ next_data_ext = extent->next_data_ext;
+ OCFS_BH_PUT_DATA(extent_bh);
+ extent = NULL;
+ extent_bh = NULL;
- for (j = 0; j < extent->next_free_ext; j++) {
- tempVbo = extent->extents[j].file_off;
- tempLbo = extent->extents[j].disk_off;
- tempSize = extent->extents[j].num_bytes;
-
- /* Add the Extent to extent map */
- bRet =
- ocfs_add_extent_map_entry (osb,
- &oin->map,
- tempVbo,
- tempLbo,
- tempSize);
- if (!bRet) {
- LOG_ERROR_STATUS (status =
- -ENOMEM);
- goto leave;
- }
- }
-
- if (extent->next_data_ext > 0) {
- if (!extent->next_data_ext) {
- LOG_ERROR_STATUS (status = -EFAIL);
- goto leave;
- }
- next_data_ext = extent->next_data_ext;
- OCFS_BH_PUT_DATA(extent_bh);
- extent = NULL;
- extent_bh = NULL;
-
- status = ocfs_read_bh(osb,
+ status = ocfs_read_bh(osb,
next_data_ext,
&extent_bh,
OCFS_BH_COND_CACHED, inode);
- if (status < 0) {
- LOG_ERROR_STATUS (status);
- goto leave;
- }
- } else
- break;
- }
+ if (status < 0) {
+ LOG_ERROR_STATUS (status);
+ goto leave;
+ }
+ } else
+ break;
}
}
- *new_oin = oin;
leave:
- if (!*new_oin && oin)
- ocfs_release_oin (oin, true);
-
/* this fe was a copy */
if (fe)
ocfs_release_file_entry (fe);
@@ -445,78 +471,6 @@
return status;
} /* ocfs_create_oin_from_entry */
-
-/*
- * ocfs_initialize_oin()
- *
- * Initialize a oin structure and file object. This function is called
- * whenever a file is recognized for the first time.
- */
-int ocfs_initialize_oin (ocfs_inode * oin, ocfs_super * osb, __u32 flags, __u64 file_off, __u64 lock_id, bool new_file, struct inode *inode)
-{
- int status = 0;
-
- LOG_ENTRY ();
-
- if (!(flags & OCFS_OIN_ROOT_DIRECTORY)) {
- status = ocfs_create_update_lock (osb, oin, lock_id, flags, new_file, inode);
- if (status < 0) {
- /* This can be okay as the other node can tell us the
- * file was deleted. */
- goto leave;
- }
- }
-
- oin->osb = osb;
- oin->oin_flags |= flags;
- oin->open_hndl_cnt = 0;
- ocfs_extent_map_init (&oin->map);
-
-leave:
- LOG_EXIT_STATUS (status);
- return status;
-} /* ocfs_initialize_oin */
-
-/*
- * ocfs_create_new_oin()
- *
- * Create a new oin.
- */
-int ocfs_create_new_oin (ocfs_inode ** Returnedoin, __u64 alloc_size, ocfs_super * osb)
-{
- int status = 0;
- ocfs_inode *oin = NULL;
-
- LOG_ENTRY_ARGS("(alloc_size = %u.%u)\n", HILO(alloc_size));
-
- OCFS_ASSERT (osb);
-
- oin = ocfs_allocate_oin ();
- *Returnedoin = oin;
-
- if (oin == NULL) {
- LOG_ERROR_STATUS (status = -ENOMEM);
- goto finally;
- }
-
- ocfs_init_sem (&(oin->main_res));
- init_MUTEX(&(oin->extend_sem));
- OCFS_SET_FLAG (oin->oin_flags, OCFS_INITIALIZED_MAIN_RESOURCE);
-
- /* Initialize the alloc size value here, file size will come
- * later in i_size */
- oin->alloc_size = alloc_size;
-
- /* Insert the pointer to osb in the oin and also Initialize
- * the OFile list */
- oin->osb = osb;
-
-finally:
-
- LOG_EXIT_STATUS (status);
- return status;
-} /* ocfs_create_new_oin */
-
/* ocfs_create_root_oin()
*
*/
@@ -524,7 +478,6 @@
{
int status = 0;
int tmpstat;
- ocfs_inode *oin = NULL;
ocfs_vol_disk_hdr *volDiskHdr = NULL;
struct buffer_head *hdr_bh = NULL;
ocfs_lock_res *LockResource = NULL;
@@ -588,36 +541,7 @@
/* if it fails, Release the memory for the OFile we allocated above */
}
- /* Create the root directory oin. This is done either here or in */
- /* FindNewoin's if it fails, Release the memory for the OFile we */
- /* allocated above */
- status = ocfs_create_new_oin (&oin, 0ULL, osb);
- if (status < 0) {
- LOG_ERROR_STATUS (status);
- goto finally;
- }
-
- /* This is for root . */
- status = ocfs_initialize_oin (oin, osb,
- OCFS_OIN_DIRECTORY | OCFS_OIN_ROOT_DIRECTORY,
- 0, osb->vol_layout.root_start_off, true, root);
- if (status < 0) {
- if (status != -EINTR)
- LOG_ERROR_STATUS (status);
- goto finally;
- }
-
- /* put the offset/inode number in the inode cache thingy. */
- ocfs_inode_hash_insert(osb, osb->vol_layout.root_start_off, 0ULL);
- // oin->Parentoin = NULL; /* Root has no parent */
-
- /* Set the Rootdirectories root Dir Node */
-
- osb->oin_root_dir = oin;
-
finally:
- if (status < 0 && oin)
- ocfs_release_oin (oin, true);
if (hdr_bh) {
lock_buffer(hdr_bh);
@@ -630,190 +554,3 @@
LOG_EXIT_STATUS (status);
return status;
} /* ocfs_create_root_oin */
-
-/*
- * ocfs_release_oin()
- *
- */
-void ocfs_release_oin (ocfs_inode * oin, bool FreeMemory)
-{
- ocfs_lock_res *lockres = NULL;
- ocfs_super *osb = NULL;
- struct inode *inode;
-
- LOG_ENTRY_ARGS ("oin = %p, free = %s\n", oin, FreeMemory? "yes" : "no");
-
- if (!oin || !oin->osb)
- goto bail;
-
- osb = oin->osb;
- lockres = oin->lock_res;
-
- if (lockres != NULL) {
- ocfs_get_lockres (lockres);
- ocfs_acquire_lockres (lockres);
- if (lockres->oin == oin)
- lockres->oin = NULL;
- ocfs_release_lockres (lockres);
- }
-
- ocfs_down_sem (&(osb->osb_res), true);
- spin_lock(&oin_num_ext_lock);
- if (oin->num_extends)
- list_del(&oin->recovery_list);
- spin_unlock(&oin_num_ext_lock);
- ocfs_up_sem (&(osb->osb_res));
-
- inode = (struct inode *) oin->inode;
-
- if (inode) {
- CLEAR_INODE_OIN(inode);
- LOG_TRACE_ARGS ("inode oin cleared / flags: %d / offset: %u.%u\n",
- inode->i_flags, GET_INODE_FEOFF(inode));
- }
-
- ocfs_extent_map_destroy (&oin->map);
-
- /* Delete the ocfs_sem objects */
- if (oin->oin_flags & OCFS_INITIALIZED_MAIN_RESOURCE) {
- ocfs_del_sem (&(oin->main_res));
- OCFS_CLEAR_FLAG (oin->oin_flags, OCFS_INITIALIZED_MAIN_RESOURCE);
- }
-
- if (FreeMemory) {
- if (oin->inode) {
- /* we don't do an iput to avoid recursive
- * calls to ocfs_put_inode */
- atomic_dec(&oin->inode->i_count);
- oin->inode = NULL;
- }
- /* clean out the oin ... why?! */
- memset(oin, 0, sizeof(ocfs_inode));
-#ifdef OCFS_MEM_DBG
- ocfs_dbg_slab_free (OcfsGlobalCtxt.oin_cache, oin);
-#else
- kmem_cache_free (OcfsGlobalCtxt.oin_cache, oin);
-#endif
- oin = NULL;
- ocfs_put_lockres (lockres);
- }
- ocfs_put_lockres (lockres);
-bail:
- LOG_EXIT ();
- return;
-} /* ocfs_release_oin */
-
-/*
- * ocfs_release_cached_oin()
- *
- */
-void ocfs_release_cached_oin (ocfs_super * osb, ocfs_inode * oin)
-{
- bool bAcquiredOIN = false;
- ocfs_lock_res *lockResource = NULL;
- ocfs_lock_res *val=NULL;
- struct dentry *dentry;
- struct list_head *iter;
- struct list_head *temp_iter;
- struct inode *inode;
- int refcount = 0;
- int status = 0;
- __u64 feoff = 0;
-
- LOG_ENTRY_ARGS ("(oin = 0x%08x)\n", oin);
-
- if (oin == NULL)
- goto bail;
-
- /*
- * If the OCFS_OSB_FLAGS_BEING_DISMOUNTED flag has
- * already been set, then the lockres hash has already
- * been cleaned out which means that we have a lock_res
- * pointer that points to free memory.
- */
- if (osb->osb_flags & OCFS_OSB_FLAGS_BEING_DISMOUNTED) {
- oin->lock_res = NULL;
- goto bail;
- }
-
- ocfs_down_sem (&(oin->main_res), true);
- bAcquiredOIN = true;
- inode = oin->inode;
-
- if (inode) {
- list_for_each_safe (iter, temp_iter, &(inode->i_dentry)) {
- dentry = list_entry (iter, struct dentry, d_alias);
- refcount += atomic_read(&dentry->d_count);
- }
- feoff = GET_INODE_FEOFF(inode);
- }
-
-
- if (refcount != 0 || oin->open_hndl_cnt != 0 ||
- oin->oin_flags & OCFS_OIN_IN_USE) {
- if (bAcquiredOIN) {
- ocfs_up_sem (&(oin->main_res));
- bAcquiredOIN = false;
- }
- goto bail;
- } else {
- OCFS_SET_FLAG (oin->oin_flags, OCFS_OIN_IN_TEARDOWN);
-
- if (bAcquiredOIN) {
- ocfs_up_sem (&(oin->main_res));
- bAcquiredOIN = false;
- }
-
- lockResource = (ocfs_lock_res *) oin->lock_res;
- if (lockResource == NULL) {
- LOG_ERROR_ARGS("lockres=null, feoff = %u.%u\n",
- HILO(feoff));
-
- goto bail;
- }
-
- if (lockResource->signature != 0x55AA) {
- LOG_ERROR_STR("Invalid lock resource");
- goto bail;
- }
- ocfs_get_lockres (lockResource);
-
- if (lockResource->sector_num == 0 || lockResource->oin != oin) {
- LOG_ERROR_STR ("id=0 or oin invalid");
- goto bail;
- }
-
- lockResource->oin = NULL;
- if (lockResource->in_cache_list) {
- list_del (& (lockResource->cache_list));
- lockResource->in_cache_list = false;
- }
-
- status = ocfs_lookup_sector_node (osb, lockResource->sector_num, &val);
- if (status >= 0) {
- if (val == lockResource)
- ocfs_remove_sector_node (osb, val);
- else
- LOG_ERROR_ARGS("(lres=0x%08x) != (val=0x%08x)",
- lockResource, val);
- ocfs_put_lockres (val);
- } else {
- if (status == -EFAIL) {
- ocfs_put_lockres (oin->lock_res);
- oin->lock_res = NULL;
- LOG_TRACE_ARGS ("hashtable already destroyed\n");
- goto bail;
- }
- LOG_ERROR_ARGS("lres=0x%08x is not in the hash!",
- lockResource);
- }
- ocfs_put_lockres (oin->lock_res);
- oin->lock_res = NULL;
- }
-
-bail:
- ocfs_put_lockres (lockResource);
- LOG_EXIT ();
- return;
-} /* ocfs_release_cached_oin */
-
Modified: branches/nooin/src/super.c
===================================================================
--- branches/nooin/src/super.c 2004-04-13 19:10:02 UTC (rev 844)
+++ branches/nooin/src/super.c 2004-04-16 01:28:18 UTC (rev 845)
@@ -124,6 +124,8 @@
MODULE_PARM_DESC(comm_voting, "Enable/Disable network dlm");
#endif /* Linux 2.4 stuff */
+extern struct semaphore recovery_list_sem;
+
static int ocfs_parse_options (char *options, __u32 * uid, __u32 * gid, bool * reclaim_id);
static int __init ocfs_driver_entry (void);
static void __exit ocfs_driver_exit (void);
@@ -220,11 +222,7 @@
goto read_super_error;
}
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
- inode = ocfs_iget(sb, NULL);
-#else
- inode = iget4(sb, OCFS_ROOT_INODE_NUMBER, 0, NULL);
-#endif
+ inode = osb->oin_root_dir->inode;
if (!inode) {
status = -EIO;
LOG_ERROR_STATUS (status);
@@ -451,6 +449,7 @@
OcfsGlobalCtxt.comm_seq_num = 0;
spin_unlock (&OcfsGlobalCtxt.comm_seq_lock);
+ init_MUTEX (&recovery_list_sem);
/* Initialize the proc interface */
ocfs_proc_init ();
@@ -740,21 +739,6 @@
}
#endif
-static void ocfs_inode_init_once(void *p, kmem_cache_t *cachep,
- unsigned long flags)
-{
- ocfs_inode_private *i = (ocfs_inode_private *) p;
-
- if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) ==
- SLAB_CTOR_CONSTRUCTOR) {
- i->oin = NULL;
- i->voteoff = 0;
- i->feoff = 0;
- i->flags = 0;
- atomic_set(&i->i_clean_buffer_seq, 0);
- }
-}
-
/*
* ocfs_initialize_mem_lists()
*
@@ -763,7 +747,7 @@
{
OcfsGlobalCtxt.inode_cache = kmem_cache_create("ocfs2_inode",
sizeof(ocfs_inode_private), 0, SLAB_NO_REAP | SLAB_HWCACHE_ALIGN,
- ocfs_inode_init_once, NULL);
+ NULL, NULL);
OcfsGlobalCtxt.oin_cache = kmem_cache_create ("ocfs2_oin",
sizeof (ocfs_inode) + OCFS_POINTER_SIZE, 0, SLAB_NO_REAP | SLAB_HWCACHE_ALIGN,
@@ -827,6 +811,7 @@
ocfs_vol_label *vol_label = NULL;
int child_pid, i;
struct buffer_head *bhs[] = { NULL, NULL };
+ struct inode *inode = NULL;
LOG_ENTRY ();
@@ -1015,6 +1000,27 @@
goto leave;
}
+ /* Initialize the root inode. */
+ ocfs_inode_hash_insert(osb, osb->vol_layout.root_start_off, 0ULL);
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
+ inode = ocfs_iget(sb, NULL);
+#else
+ inode = iget4(sb, OCFS_ROOT_INODE_NUMBER, 0, NULL);
+#endif
+ if (!inode) {
+ status = -EIO;
+ LOG_ERROR_STATUS (status);
+ goto leave;
+ }
+ if (is_bad_inode(inode)) {
+ status = -EIO;
+ LOG_ERROR_STATUS (status);
+ iput(inode);
+ inode = NULL;
+ goto leave;
+ }
+ osb->oin_root_dir = GET_INODE_OIN(inode);
+
/* Read the publish sector for this node and cleanup dirent being */
/* modified when we crashed. */
LOG_TRACE_STR ("ocfs_check_volume...");
@@ -1119,7 +1125,6 @@
LOG_ERROR_STR("Could not set mounted flag!");
ocfs_sync_blockdev(sb);
- ocfs_release_oin (rootoin, true);
/* Destroy the Hash table */
ocfs_hash_destroy (&(osb->root_sect_node), lockres_hash_free_func);
More information about the Ocfs2-commits
mailing list