[Ocfs2-devel] [PATCH 0/9 v6] ocfs2: support append O_DIRECT write

2015-01-20 Thread Joseph Qi
Currently in case of append O_DIRECT write (block not allocated yet),
ocfs2 will fall back to buffered I/O. This has some disadvantages.
Firstly, it is not the behavior as expected.
Secondly, it will consume huge page cache, e.g. in mass backup scenario.
Thirdly, modern filesystems such as ext4 support this feature.

In this patch set, the direct I/O write doesn't fallback to buffer I/O
write any more because the allocate blocks are enabled in direct I/O
now.

changelog:
v6 <- v5:
-- Take Mark's advice to use prefix "dio-" to distinguish dio orphan
   entry from unlink/rename.
-- Take Mark's advice to treat this feature as a ro compat feature.
-- Fix a bug in case of not cluster aligned io, cluster_align should
   be !zero_len, not !!zero_len.
-- Fix a bug in case of fallocate with FALLOC_FL_KEEP_SIZE.
-- Fix the wrong *ppos and written when completing the rest request
   using buffer io.

Corresponding ocfs2 tools (mkfs.ocfs2, tunefs.ocfs2, fsck.ocfs2, etc.)
will be updated later.


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 1/9 v6] ocfs2: prepare some interfaces used in append direct io

2015-01-20 Thread Joseph Qi
Prepare some interfaces which will be used in append O_DIRECT write.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/file.c | 11 +--
 fs/ocfs2/file.h |  9 +
 2 files changed, 18 insertions(+), 2 deletions(-)

diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c
index 3950693..d0ed2c1 100644
--- a/fs/ocfs2/file.c
+++ b/fs/ocfs2/file.c
@@ -295,7 +295,7 @@ out:
return ret;
 }

-static int ocfs2_set_inode_size(handle_t *handle,
+int ocfs2_set_inode_size(handle_t *handle,
struct inode *inode,
struct buffer_head *fe_bh,
u64 new_i_size)
@@ -441,7 +441,7 @@ out:
return status;
 }

-static int ocfs2_truncate_file(struct inode *inode,
+int ocfs2_truncate_file(struct inode *inode,
   struct buffer_head *di_bh,
   u64 new_i_size)
 {
@@ -709,6 +709,13 @@ leave:
return status;
 }

+int ocfs2_extend_allocation(struct inode *inode, u32 logical_start,
+   u32 clusters_to_add, int mark_unwritten)
+{
+   return __ocfs2_extend_allocation(inode, logical_start,
+   clusters_to_add, mark_unwritten);
+}
+
 /*
  * While a write will already be ordering the data, a truncate will not.
  * Thus, we need to explicitly order the zeroed pages.
diff --git a/fs/ocfs2/file.h b/fs/ocfs2/file.h
index 97bf761..e8c62f2 100644
--- a/fs/ocfs2/file.h
+++ b/fs/ocfs2/file.h
@@ -51,13 +51,22 @@ int ocfs2_add_inode_data(struct ocfs2_super *osb,
 struct ocfs2_alloc_context *data_ac,
 struct ocfs2_alloc_context *meta_ac,
 enum ocfs2_alloc_restarted *reason_ret);
+int ocfs2_set_inode_size(handle_t *handle,
+   struct inode *inode,
+   struct buffer_head *fe_bh,
+   u64 new_i_size);
 int ocfs2_simple_size_update(struct inode *inode,
 struct buffer_head *di_bh,
 u64 new_i_size);
+int ocfs2_truncate_file(struct inode *inode,
+   struct buffer_head *di_bh,
+   u64 new_i_size);
 int ocfs2_extend_no_holes(struct inode *inode, struct buffer_head *di_bh,
  u64 new_i_size, u64 zero_to);
 int ocfs2_zero_extend(struct inode *inode, struct buffer_head *di_bh,
  loff_t zero_to);
+int ocfs2_extend_allocation(struct inode *inode, u32 logical_start,
+   u32 clusters_to_add, int mark_unwritten);
 int ocfs2_setattr(struct dentry *dentry, struct iattr *attr);
 int ocfs2_getattr(struct vfsmount *mnt, struct dentry *dentry,
  struct kstat *stat);
-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 2/9 v6] ocfs2: add functions to add and remove inode in orphan dir

2015-01-20 Thread Joseph Qi
Add functions to add inode to orphan dir and remove inode in orphan dir.
Here we do not call ocfs2_prepare_orphan_dir and ocfs2_orphan_add
directly.  Because append O_DIRECT will add inode to orphan two and may
result in more than one orphan entry for the same inode.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/inode.c|   2 +-
 fs/ocfs2/journal.h  |   5 ++
 fs/ocfs2/namei.c| 248 ++--
 fs/ocfs2/namei.h|   8 +-
 fs/ocfs2/ocfs2_fs.h |   6 +-
 5 files changed, 239 insertions(+), 30 deletions(-)

diff --git a/fs/ocfs2/inode.c b/fs/ocfs2/inode.c
index c8b25de..3025c0d 100644
--- a/fs/ocfs2/inode.c
+++ b/fs/ocfs2/inode.c
@@ -648,7 +648,7 @@ static int ocfs2_remove_inode(struct inode *inode,

if (!(OCFS2_I(inode)->ip_flags & OCFS2_INODE_SKIP_ORPHAN_DIR)) {
status = ocfs2_orphan_del(osb, handle, orphan_dir_inode, inode,
- orphan_dir_bh);
+ orphan_dir_bh, false);
if (status < 0) {
mlog_errno(status);
goto bail_commit;
diff --git a/fs/ocfs2/journal.h b/fs/ocfs2/journal.h
index 7f8cde9..f4cd3c3 100644
--- a/fs/ocfs2/journal.h
+++ b/fs/ocfs2/journal.h
@@ -472,6 +472,11 @@ static inline int ocfs2_unlink_credits(struct super_block 
*sb)
  * orphan dir index leaf */
 #define OCFS2_DELETE_INODE_CREDITS (3 * OCFS2_INODE_UPDATE_CREDITS + 4)

+/* dinode + orphan dir dinode + extent tree leaf block + orphan dir entry +
+ * orphan dir index root + orphan dir index leaf */
+#define OCFS2_INODE_ADD_TO_ORPHAN_CREDITS  (2 * OCFS2_INODE_UPDATE_CREDITS + 4)
+#define OCFS2_INODE_DEL_FROM_ORPHAN_CREDITS  OCFS2_INODE_ADD_TO_ORPHAN_CREDITS
+
 /* dinode update, old dir dinode update, new dir dinode update, old
  * dir dir entry, new dir dir entry, dir entry update for renaming
  * directory + target unlink + 3 x dir index leaves */
diff --git a/fs/ocfs2/namei.c b/fs/ocfs2/namei.c
index 914c121..b069d6d 100644
--- a/fs/ocfs2/namei.c
+++ b/fs/ocfs2/namei.c
@@ -79,7 +79,8 @@ static int ocfs2_prepare_orphan_dir(struct ocfs2_super *osb,
struct inode **ret_orphan_dir,
u64 blkno,
char *name,
-   struct ocfs2_dir_lookup_result *lookup);
+   struct ocfs2_dir_lookup_result *lookup,
+   bool dio);

 static int ocfs2_orphan_add(struct ocfs2_super *osb,
handle_t *handle,
@@ -87,7 +88,8 @@ static int ocfs2_orphan_add(struct ocfs2_super *osb,
struct buffer_head *fe_bh,
char *name,
struct ocfs2_dir_lookup_result *lookup,
-   struct inode *orphan_dir_inode);
+   struct inode *orphan_dir_inode,
+   bool dio);

 static int ocfs2_create_symlink_data(struct ocfs2_super *osb,
 handle_t *handle,
@@ -104,6 +106,8 @@ static int ocfs2_double_lock(struct ocfs2_super *osb,
 static void ocfs2_double_unlock(struct inode *inode1, struct inode *inode2);
 /* An orphan dir name is an 8 byte value, printed as a hex string */
 #define OCFS2_ORPHAN_NAMELEN ((int)(2 * sizeof(u64)))
+#define OCFS2_DIO_ORPHAN_PREFIX "dio-"
+#define OCFS2_DIO_ORPHAN_PREFIX_LEN 4

 static struct dentry *ocfs2_lookup(struct inode *dir, struct dentry *dentry,
   unsigned int flags)
@@ -952,7 +956,8 @@ static int ocfs2_unlink(struct inode *dir,
if (ocfs2_inode_is_unlinkable(inode)) {
status = ocfs2_prepare_orphan_dir(osb, &orphan_dir,
  OCFS2_I(inode)->ip_blkno,
- orphan_name, &orphan_insert);
+ orphan_name, &orphan_insert,
+ false);
if (status < 0) {
mlog_errno(status);
goto leave;
@@ -1004,7 +1009,7 @@ static int ocfs2_unlink(struct inode *dir,

if (is_unlinkable) {
status = ocfs2_orphan_add(osb, handle, inode, fe_bh,
-   orphan_name, &orphan_insert, orphan_dir);
+   orphan_name, &orphan_insert, orphan_dir, false);
if (status < 0)
mlog_errno(status);
}
@@ -1440,7 +1445,8 @@ static int ocfs2_rename(struct inode *old_dir,
if (S_ISDIR(new_inode->i_mode) || (new_inode->i_nlink == 1)) {
status = ocfs2_prepare_orphan_dir(osb, &orphan_dir,
OCFS2_I(new_inode)->ip_blkno,
-   orphan_name, &orph

[Ocfs2-devel] [PATCH 3/9 v6] ocfs2: add orphan recovery types in ocfs2_recover_orphans

2015-01-20 Thread Joseph Qi
Define two orphan recovery types, which indicates if need truncate file or
not.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/journal.c | 108 +++--
 fs/ocfs2/ocfs2.h   |   5 +++
 2 files changed, 93 insertions(+), 20 deletions(-)

diff --git a/fs/ocfs2/journal.c b/fs/ocfs2/journal.c
index 4f50238..1163127 100644
--- a/fs/ocfs2/journal.c
+++ b/fs/ocfs2/journal.c
@@ -50,6 +50,8 @@
 #include "sysfile.h"
 #include "uptodate.h"
 #include "quota.h"
+#include "file.h"
+#include "namei.h"

 #include "buffer_head_io.h"
 #include "ocfs2_trace.h"
@@ -69,13 +71,15 @@ static int ocfs2_journal_toggle_dirty(struct ocfs2_super 
*osb,
 static int ocfs2_trylock_journal(struct ocfs2_super *osb,
 int slot_num);
 static int ocfs2_recover_orphans(struct ocfs2_super *osb,
-int slot);
+int slot,
+enum ocfs2_orphan_reco_type orphan_reco_type);
 static int ocfs2_commit_thread(void *arg);
 static void ocfs2_queue_recovery_completion(struct ocfs2_journal *journal,
int slot_num,
struct ocfs2_dinode *la_dinode,
struct ocfs2_dinode *tl_dinode,
-   struct ocfs2_quota_recovery *qrec);
+   struct ocfs2_quota_recovery *qrec,
+   enum ocfs2_orphan_reco_type 
orphan_reco_type);

 static inline int ocfs2_wait_on_mount(struct ocfs2_super *osb)
 {
@@ -149,7 +153,8 @@ int ocfs2_compute_replay_slots(struct ocfs2_super *osb)
return 0;
 }

-void ocfs2_queue_replay_slots(struct ocfs2_super *osb)
+void ocfs2_queue_replay_slots(struct ocfs2_super *osb,
+   enum ocfs2_orphan_reco_type orphan_reco_type)
 {
struct ocfs2_replay_map *replay_map = osb->replay_map;
int i;
@@ -163,7 +168,8 @@ void ocfs2_queue_replay_slots(struct ocfs2_super *osb)
for (i = 0; i < replay_map->rm_slots; i++)
if (replay_map->rm_replay_slots[i])
ocfs2_queue_recovery_completion(osb->journal, i, NULL,
-   NULL, NULL);
+   NULL, NULL,
+   orphan_reco_type);
replay_map->rm_state = REPLAY_DONE;
 }

@@ -1174,6 +1180,7 @@ struct ocfs2_la_recovery_item {
struct ocfs2_dinode *lri_la_dinode;
struct ocfs2_dinode *lri_tl_dinode;
struct ocfs2_quota_recovery *lri_qrec;
+   enum ocfs2_orphan_reco_type  lri_orphan_reco_type;
 };

 /* Does the second half of the recovery process. By this point, the
@@ -1195,6 +1202,7 @@ void ocfs2_complete_recovery(struct work_struct *work)
struct ocfs2_dinode *la_dinode, *tl_dinode;
struct ocfs2_la_recovery_item *item, *n;
struct ocfs2_quota_recovery *qrec;
+   enum ocfs2_orphan_reco_type orphan_reco_type;
LIST_HEAD(tmp_la_list);

trace_ocfs2_complete_recovery(
@@ -1212,6 +1220,7 @@ void ocfs2_complete_recovery(struct work_struct *work)
la_dinode = item->lri_la_dinode;
tl_dinode = item->lri_tl_dinode;
qrec = item->lri_qrec;
+   orphan_reco_type = item->lri_orphan_reco_type;

trace_ocfs2_complete_recovery_slot(item->lri_slot,
la_dinode ? le64_to_cpu(la_dinode->i_blkno) : 0,
@@ -1236,7 +1245,8 @@ void ocfs2_complete_recovery(struct work_struct *work)
kfree(tl_dinode);
}

-   ret = ocfs2_recover_orphans(osb, item->lri_slot);
+   ret = ocfs2_recover_orphans(osb, item->lri_slot,
+   orphan_reco_type);
if (ret < 0)
mlog_errno(ret);

@@ -1261,7 +1271,8 @@ static void ocfs2_queue_recovery_completion(struct 
ocfs2_journal *journal,
int slot_num,
struct ocfs2_dinode *la_dinode,
struct ocfs2_dinode *tl_dinode,
-   struct ocfs2_quota_recovery *qrec)
+   struct ocfs2_quota_recovery *qrec,
+   enum ocfs2_orphan_reco_type 
orphan_reco_type)
 {
struct ocfs2_la_recovery_item *item;

@@ -1285,6 +1296,7 @@ static void ocfs2_queue_recovery_completion(struct 
ocfs2_journal *journal,
item->lri_slot = slot_num;
item->lri_tl_dinode = tl_dinode;
item->lri_qrec = qrec;
+   item->lri_orphan_reco_type = orphan_reco_type;

spin_lock(&journal->j_lock);
list_add_tail(&item->lri_list, &journal->j_la_cleanups);
@@ -13

[Ocfs2-devel] [PATCH 5/9 v6] ocfs2: allocate blocks in ocfs2_direct_IO_get_blocks

2015-01-20 Thread Joseph Qi
Allow blocks allocation in ocfs2_direct_IO_get_blocks.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/aops.c | 45 ++---
 1 file changed, 42 insertions(+), 3 deletions(-)

diff --git a/fs/ocfs2/aops.c b/fs/ocfs2/aops.c
index 8b464fe..fc2e5ac 100644
--- a/fs/ocfs2/aops.c
+++ b/fs/ocfs2/aops.c
@@ -510,18 +510,21 @@ bail:
  *
  * called like this: dio->get_blocks(dio->inode, fs_startblk,
  * fs_count, map_bh, dio->rw == WRITE);
- *
- * Note that we never bother to allocate blocks here, and thus ignore the
- * create argument.
  */
 static int ocfs2_direct_IO_get_blocks(struct inode *inode, sector_t iblock,
 struct buffer_head *bh_result, int create)
 {
int ret;
+   u32 cpos = 0;
+   int alloc_locked = 0;
u64 p_blkno, inode_blocks, contig_blocks;
unsigned int ext_flags;
unsigned char blocksize_bits = inode->i_sb->s_blocksize_bits;
unsigned long max_blocks = bh_result->b_size >> inode->i_blkbits;
+   unsigned long len = bh_result->b_size;
+   unsigned int clusters_to_alloc = 0;
+
+   cpos = ocfs2_blocks_to_clusters(inode->i_sb, iblock);

/* This function won't even be called if the request isn't all
 * nicely aligned and of the right size, so there's no need
@@ -543,6 +546,40 @@ static int ocfs2_direct_IO_get_blocks(struct inode *inode, 
sector_t iblock,
/* We should already CoW the refcounted extent in case of create. */
BUG_ON(create && (ext_flags & OCFS2_EXT_REFCOUNTED));

+   /* allocate blocks if no p_blkno is found, and create == 1 */
+   if (!p_blkno && create) {
+   ret = ocfs2_inode_lock(inode, NULL, 1);
+   if (ret < 0) {
+   mlog_errno(ret);
+   goto bail;
+   }
+
+   alloc_locked = 1;
+
+   /* fill hole, allocate blocks can't be larger than the size
+* of the hole */
+   clusters_to_alloc = ocfs2_clusters_for_bytes(inode->i_sb, len);
+   if (clusters_to_alloc > contig_blocks)
+   clusters_to_alloc = contig_blocks;
+
+   /* allocate extent and insert them into the extent tree */
+   ret = ocfs2_extend_allocation(inode, cpos,
+   clusters_to_alloc, 0);
+   if (ret < 0) {
+   mlog_errno(ret);
+   goto bail;
+   }
+
+   ret = ocfs2_extent_map_get_blocks(inode, iblock, &p_blkno,
+   &contig_blocks, &ext_flags);
+   if (ret < 0) {
+   mlog(ML_ERROR, "get_blocks() failed iblock=%llu\n",
+   (unsigned long long)iblock);
+   ret = -EIO;
+   goto bail;
+   }
+   }
+
/*
 * get_more_blocks() expects us to describe a hole by clearing
 * the mapped bit on bh_result().
@@ -560,6 +597,8 @@ static int ocfs2_direct_IO_get_blocks(struct inode *inode, 
sector_t iblock,
contig_blocks = max_blocks;
bh_result->b_size = contig_blocks << blocksize_bits;
 bail:
+   if (alloc_locked)
+   ocfs2_inode_unlock(inode, 1);
return ret;
 }

-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 4/9 v6] ocfs2: implement ocfs2_direct_IO_write

2015-01-20 Thread Joseph Qi
Implement ocfs2_direct_IO_write.  Add the inode to orphan dir first, and
then delete it once append O_DIRECT finished.

This is to make sure block allocation and inode size are consistent.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/aops.c  | 198 ++-
 fs/ocfs2/ocfs2.h |  10 +++
 2 files changed, 205 insertions(+), 3 deletions(-)

diff --git a/fs/ocfs2/aops.c b/fs/ocfs2/aops.c
index 46d93e9..8b464fe 100644
--- a/fs/ocfs2/aops.c
+++ b/fs/ocfs2/aops.c
@@ -28,6 +28,7 @@
 #include 
 #include 
 #include 
+#include 

 #include 

@@ -47,6 +48,9 @@
 #include "ocfs2_trace.h"

 #include "buffer_head_io.h"
+#include "dir.h"
+#include "namei.h"
+#include "sysfile.h"

 static int ocfs2_symlink_get_block(struct inode *inode, sector_t iblock,
   struct buffer_head *bh_result, int create)
@@ -597,6 +601,185 @@ static int ocfs2_releasepage(struct page *page, gfp_t 
wait)
return try_to_free_buffers(page);
 }

+static int ocfs2_is_overwrite(struct ocfs2_super *osb,
+   struct inode *inode, loff_t offset)
+{
+   int ret = 0;
+   u32 v_cpos = 0;
+   u32 p_cpos = 0;
+   unsigned int num_clusters = 0;
+   unsigned int ext_flags = 0;
+
+   v_cpos = ocfs2_bytes_to_clusters(osb->sb, offset);
+   ret = ocfs2_get_clusters(inode, v_cpos, &p_cpos,
+   &num_clusters, &ext_flags);
+   if (ret < 0) {
+   mlog_errno(ret);
+   return ret;
+   }
+
+   if (p_cpos && !(ext_flags & OCFS2_EXT_UNWRITTEN))
+   return 1;
+
+   return 0;
+}
+
+static ssize_t ocfs2_direct_IO_write(struct kiocb *iocb,
+   struct iov_iter *iter,
+   loff_t offset)
+{
+   ssize_t ret = 0;
+   ssize_t written = 0;
+   bool orphaned = false;
+   int is_overwrite = 0;
+   struct file *file = iocb->ki_filp;
+   struct inode *inode = file_inode(file)->i_mapping->host;
+   struct ocfs2_super *osb = OCFS2_SB(inode->i_sb);
+   struct buffer_head *di_bh = NULL;
+   size_t count = iter->count;
+   journal_t *journal = osb->journal->j_journal;
+   u32 zero_len;
+   int cluster_align;
+   loff_t final_size = offset + count;
+   int append_write = offset >= i_size_read(inode) ? 1 : 0;
+   unsigned int num_clusters = 0;
+   unsigned int ext_flags = 0;
+
+   {
+   u64 o = offset;
+
+   zero_len = do_div(o, 1 << osb->s_clustersize_bits);
+   cluster_align = !zero_len;
+   }
+
+   /*
+* when final_size > inode->i_size, inode->i_size will be
+* updated after direct write, so add the inode to orphan
+* dir first.
+*/
+   if (final_size > i_size_read(inode)) {
+   ret = ocfs2_add_inode_to_orphan(osb, inode);
+   if (ret < 0) {
+   mlog_errno(ret);
+   goto out;
+   }
+   orphaned = true;
+   }
+
+   if (append_write) {
+   ret = ocfs2_inode_lock(inode, &di_bh, 1);
+   if (ret < 0) {
+   mlog_errno(ret);
+   goto clean_orphan;
+   }
+
+   if (ocfs2_sparse_alloc(OCFS2_SB(inode->i_sb)))
+   ret = ocfs2_zero_extend(inode, di_bh, offset);
+   else
+   ret = ocfs2_extend_no_holes(inode, di_bh, offset,
+   offset);
+   if (ret < 0) {
+   mlog_errno(ret);
+   ocfs2_inode_unlock(inode, 1);
+   brelse(di_bh);
+   goto clean_orphan;
+   }
+
+   is_overwrite = ocfs2_is_overwrite(osb, inode, offset);
+   if (is_overwrite < 0) {
+   mlog_errno(is_overwrite);
+   ocfs2_inode_unlock(inode, 1);
+   brelse(di_bh);
+   goto clean_orphan;
+   }
+
+   ocfs2_inode_unlock(inode, 1);
+   brelse(di_bh);
+   di_bh = NULL;
+   }
+
+   written = __blockdev_direct_IO(WRITE, iocb, inode, inode->i_sb->s_bdev,
+   iter, offset,
+   ocfs2_direct_IO_get_blocks,
+   ocfs2_dio_end_io, NULL, 0);
+   if (unlikely(written < 0)) {
+   loff_t i_size = i_size_read(inode);
+
+   if (offset + count > i_size) {
+   ret = ocfs2_inode_lock(inode, &di_bh, 1);
+   if (ret < 0) {
+   mlog_errno(ret);
+   goto clean_orphan;
+   }
+
+   if (i_size == i_size_read(inode)) {
+   ret = ocfs2_truncate_file(inode, di_bh,
+   i_size);
+  

[Ocfs2-devel] [PATCH 7/9 v6] ocfs2: complete the rest request through buffer io

2015-01-20 Thread Joseph Qi
Complte the rest request thourgh buffer io after direct write performed.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/file.c | 43 ++-
 1 file changed, 42 insertions(+), 1 deletion(-)

diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c
index c1446cf..4a712cf 100644
--- a/fs/ocfs2/file.c
+++ b/fs/ocfs2/file.c
@@ -2253,6 +2253,7 @@ static ssize_t ocfs2_file_write_iter(struct kiocb *iocb,
u32 old_clusters;
struct file *file = iocb->ki_filp;
struct inode *inode = file_inode(file);
+   struct address_space *mapping = file->f_mapping;
struct ocfs2_super *osb = OCFS2_SB(inode->i_sb);
int full_coherency = !(osb->s_mount_opt &
   OCFS2_MOUNT_COHERENCY_BUFFERED);
@@ -2367,11 +2368,51 @@ relock:

iov_iter_truncate(from, count);
if (direct_io) {
+   loff_t endbyte;
+   ssize_t written_buffered;
written = generic_file_direct_write(iocb, from, *ppos);
-   if (written < 0) {
+   if (written < 0 || written == count) {
ret = written;
goto out_dio;
}
+
+   /*
+* for completing the rest of the request.
+*/
+   *ppos += written;
+   count -= written;
+   written_buffered = generic_perform_write(file, from, *ppos);
+   /*
+* If generic_file_buffered_write() returned a synchronous error
+* then we want to return the number of bytes which were
+* direct-written, or the error code if that was zero. Note
+* that this differs from normal direct-io semantics, which
+* will return -EFOO even if some bytes were written.
+*/
+   if (written_buffered < 0) {
+   ret = written_buffered;
+   goto out_dio;
+   }
+
+   iocb->ki_pos = *ppos + written_buffered;
+   /* We need to ensure that the page cache pages are written to
+* disk and invalidated to preserve the expected O_DIRECT
+* semantics.
+*/
+   endbyte = *ppos + written_buffered - 1;
+   ret = filemap_write_and_wait_range(file->f_mapping, *ppos,
+   endbyte);
+   if (ret == 0) {
+   written += written_buffered;
+   invalidate_mapping_pages(mapping,
+   *ppos >> PAGE_CACHE_SHIFT,
+   endbyte >> PAGE_CACHE_SHIFT);
+   } else {
+   /*
+* We don't know how much we wrote, so just return
+* the number of bytes which were direct-written
+*/
+   }
} else {
current->backing_dev_info = file->f_mapping->backing_dev_info;
written = generic_perform_write(file, from, *ppos);
-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 8/9 v6] ocfs2: wait for orphan recovery first once append O_DIRECT write crash

2015-01-20 Thread Joseph Qi
If one node has crashed with orphan entry leftover, another node which do
append O_DIRECT write to the same file will override the
i_dio_orphaned_slot.  Then the old entry won't be cleaned forever. If
this case happens, we let it wait for orphan recovery first.

Cc: Weiwei Wang 
Signed-off-by: Joseph Qi 
---
 fs/ocfs2/inode.h   |  2 ++
 fs/ocfs2/journal.c |  2 ++
 fs/ocfs2/namei.c   | 37 +
 fs/ocfs2/super.c   |  2 ++
 4 files changed, 43 insertions(+)

diff --git a/fs/ocfs2/inode.h b/fs/ocfs2/inode.h
index ca3431e..5e86b24 100644
--- a/fs/ocfs2/inode.h
+++ b/fs/ocfs2/inode.h
@@ -81,6 +81,8 @@ struct ocfs2_inode_info
tid_t i_sync_tid;
tid_t i_datasync_tid;

+   wait_queue_head_t append_dio_wq;
+
struct dquot *i_dquot[MAXQUOTAS];
 };

diff --git a/fs/ocfs2/journal.c b/fs/ocfs2/journal.c
index 1163127..ca11c83 100644
--- a/fs/ocfs2/journal.c
+++ b/fs/ocfs2/journal.c
@@ -2205,6 +2205,8 @@ static int ocfs2_recover_orphans(struct ocfs2_super *osb,
ret = ocfs2_del_inode_from_orphan(osb, inode, 0, 0);
if (ret)
mlog_errno(ret);
+
+   wake_up(&OCFS2_I(inode)->append_dio_wq);
} /* else if ORPHAN_NO_NEED_TRUNCATE, do nothing */

 next:
diff --git a/fs/ocfs2/namei.c b/fs/ocfs2/namei.c
index b069d6d..873b40a 100644
--- a/fs/ocfs2/namei.c
+++ b/fs/ocfs2/namei.c
@@ -2578,6 +2578,27 @@ leave:
return status;
 }

+static int ocfs2_dio_orphan_recovered(struct inode *inode)
+{
+   int ret;
+   struct buffer_head *di_bh = NULL;
+   struct ocfs2_dinode *di = NULL;
+
+   ret = ocfs2_inode_lock(inode, &di_bh, 1);
+   if (ret < 0) {
+   mlog_errno(ret);
+   return 0;
+   }
+
+   di = (struct ocfs2_dinode *) di_bh->b_data;
+   ret = !(di->i_flags & cpu_to_le32(OCFS2_DIO_ORPHANED_FL));
+   ocfs2_inode_unlock(inode, 1);
+   brelse(di_bh);
+
+   return ret;
+}
+
+#define OCFS2_DIO_ORPHANED_FL_CHECK_INTERVAL 1
 int ocfs2_add_inode_to_orphan(struct ocfs2_super *osb,
struct inode *inode)
 {
@@ -2587,13 +2608,29 @@ int ocfs2_add_inode_to_orphan(struct ocfs2_super *osb,
struct buffer_head *di_bh = NULL;
int status = 0;
handle_t *handle = NULL;
+   struct ocfs2_dinode *di = NULL;

+restart:
status = ocfs2_inode_lock(inode, &di_bh, 1);
if (status < 0) {
mlog_errno(status);
goto bail;
}

+   di = (struct ocfs2_dinode *) di_bh->b_data;
+   /*
+* Another append dio crashed?
+* If so, wait for recovery first.
+*/
+   if (unlikely(di->i_flags & cpu_to_le32(OCFS2_DIO_ORPHANED_FL))) {
+   ocfs2_inode_unlock(inode, 1);
+   brelse(di_bh);
+   wait_event_interruptible_timeout(OCFS2_I(inode)->append_dio_wq,
+   ocfs2_dio_orphan_recovered(inode),
+   
msecs_to_jiffies(OCFS2_DIO_ORPHANED_FL_CHECK_INTERVAL));
+   goto restart;
+   }
+
status = ocfs2_prepare_orphan_dir(osb, &orphan_dir_inode,
OCFS2_I(inode)->ip_blkno,
orphan_name,
diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c
index 8372317..04ee6d1 100644
--- a/fs/ocfs2/super.c
+++ b/fs/ocfs2/super.c
@@ -1768,6 +1768,8 @@ static void ocfs2_inode_init_once(void *data)
ocfs2_lock_res_init_once(&oi->ip_inode_lockres);
ocfs2_lock_res_init_once(&oi->ip_open_lockres);

+   init_waitqueue_head(&oi->append_dio_wq);
+
ocfs2_metadata_cache_init(INODE_CACHE(&oi->vfs_inode),
  &ocfs2_inode_caching_ops);

-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 0/9 v6] ocfs2: support append O_DIRECT write

2015-01-20 Thread Junxiao Bi
Hi Joseph,

Did this version make any performance improvement with v5? I tested v5,
and it didn't improve performance with original buffer write + sync.

Thanks,
Junxiao.

On 01/20/2015 04:01 PM, Joseph Qi wrote:
> Currently in case of append O_DIRECT write (block not allocated yet),
> ocfs2 will fall back to buffered I/O. This has some disadvantages.
> Firstly, it is not the behavior as expected.
> Secondly, it will consume huge page cache, e.g. in mass backup scenario.
> Thirdly, modern filesystems such as ext4 support this feature.
> 
> In this patch set, the direct I/O write doesn't fallback to buffer I/O
> write any more because the allocate blocks are enabled in direct I/O
> now.
> 
> changelog:
> v6 <- v5:
> -- Take Mark's advice to use prefix "dio-" to distinguish dio orphan
>entry from unlink/rename.
> -- Take Mark's advice to treat this feature as a ro compat feature.
> -- Fix a bug in case of not cluster aligned io, cluster_align should
>be !zero_len, not !!zero_len.
> -- Fix a bug in case of fallocate with FALLOC_FL_KEEP_SIZE.
> -- Fix the wrong *ppos and written when completing the rest request
>using buffer io.
> 
> Corresponding ocfs2 tools (mkfs.ocfs2, tunefs.ocfs2, fsck.ocfs2, etc.)
> will be updated later.
> 
> 
> ___
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> https://oss.oracle.com/mailman/listinfo/ocfs2-devel
> 


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 9/9 v6] ocfs2: set append dio as a ro compat feature

2015-01-20 Thread Joseph Qi
Intruduce a bit OCFS2_FEATURE_RO_COMPAT_APPEND_DIO and check it in
write flow. If the bit is not set, fall back to the old way.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/file.c | 17 -
 fs/ocfs2/ocfs2.h|  8 
 fs/ocfs2/ocfs2_fs.h |  8 +++-
 3 files changed, 31 insertions(+), 2 deletions(-)

diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c
index 4a712cf..41700d8 100644
--- a/fs/ocfs2/file.c
+++ b/fs/ocfs2/file.c
@@ -2213,6 +2213,15 @@ static int ocfs2_prepare_inode_for_write(struct file 
*file,
}

/*
+* Fallback to old way if the feature bit is not set.
+*/
+   if (end > i_size_read(inode) &&
+   !ocfs2_supports_append_dio(osb)) {
+   *direct_io = 0;
+   break;
+   }
+
+   /*
 * We don't fill holes during direct io, so
 * check for them here. If any are found, the
 * caller will have to retake some cluster
@@ -2220,7 +2229,13 @@ static int ocfs2_prepare_inode_for_write(struct file 
*file,
 */
ret = ocfs2_check_range_for_holes(inode, saved_pos, count);
if (ret == 1) {
-   *direct_io = 0;
+   /*
+* Fallback to old way if the feature bit is not set.
+* Otherwise try dio first and then complete the rest
+* request through buffer io.
+*/
+   if (!ocfs2_supports_append_dio(osb))
+   *direct_io = 0;
ret = 0;
} else if (ret < 0)
mlog_errno(ret);
diff --git a/fs/ocfs2/ocfs2.h b/fs/ocfs2/ocfs2.h
index 131cc1c..bcc1cd6 100644
--- a/fs/ocfs2/ocfs2.h
+++ b/fs/ocfs2/ocfs2.h
@@ -498,6 +498,14 @@ static inline int ocfs2_writes_unwritten_extents(struct 
ocfs2_super *osb)
return 0;
 }

+static inline int ocfs2_supports_append_dio(struct ocfs2_super *osb)
+{
+   if (osb->s_feature_ro_compat & OCFS2_FEATURE_RO_COMPAT_APPEND_DIO)
+   return 1;
+   return 0;
+}
+
+
 static inline int ocfs2_supports_inline_data(struct ocfs2_super *osb)
 {
if (osb->s_feature_incompat & OCFS2_FEATURE_INCOMPAT_INLINE_DATA)
diff --git a/fs/ocfs2/ocfs2_fs.h b/fs/ocfs2/ocfs2_fs.h
index cf4fa43..20e37a3 100644
--- a/fs/ocfs2/ocfs2_fs.h
+++ b/fs/ocfs2/ocfs2_fs.h
@@ -105,7 +105,8 @@
 | OCFS2_FEATURE_INCOMPAT_CLUSTERINFO)
 #define OCFS2_FEATURE_RO_COMPAT_SUPP   (OCFS2_FEATURE_RO_COMPAT_UNWRITTEN \
 | OCFS2_FEATURE_RO_COMPAT_USRQUOTA \
-| OCFS2_FEATURE_RO_COMPAT_GRPQUOTA)
+| OCFS2_FEATURE_RO_COMPAT_GRPQUOTA \
+| OCFS2_FEATURE_RO_COMPAT_APPEND_DIO)

 /*
  * Heartbeat-only devices are missing journals and other files.  The
@@ -199,6 +200,11 @@
 #define OCFS2_FEATURE_RO_COMPAT_USRQUOTA   0x0002
 #define OCFS2_FEATURE_RO_COMPAT_GRPQUOTA   0x0004

+/*
+ * Append Direct IO support
+ */
+#define OCFS2_FEATURE_RO_COMPAT_APPEND_DIO 0x0008
+
 /* The byte offset of the first backup block will be 1G.
  * The following will be 4G, 16G, 64G, 256G and 1T.
  */
-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 0/9 v6] ocfs2: support append O_DIRECT write

2015-01-20 Thread Joseph Qi
Hi Junxiao,

On 2015/1/20 16:26, Junxiao Bi wrote:
> Hi Joseph,
> 
> Did this version make any performance improvement with v5? I tested v5,
> and it didn't improve performance with original buffer write + sync.
No performance difference between these two versions.
But we have tested with fio before, it shows about 5% performance
improvement with normal buffer write (without sync).
As I described, this feature is not truly for performance improvement.
We aim to reduce the host page cache consumption. For example, dom0
in virtualization case which won't be configured too much memory.

--
Joseph
> 
> Thanks,
> Junxiao.
> 
> On 01/20/2015 04:01 PM, Joseph Qi wrote:
>> Currently in case of append O_DIRECT write (block not allocated yet),
>> ocfs2 will fall back to buffered I/O. This has some disadvantages.
>> Firstly, it is not the behavior as expected.
>> Secondly, it will consume huge page cache, e.g. in mass backup scenario.
>> Thirdly, modern filesystems such as ext4 support this feature.
>>
>> In this patch set, the direct I/O write doesn't fallback to buffer I/O
>> write any more because the allocate blocks are enabled in direct I/O
>> now.
>>
>> changelog:
>> v6 <- v5:
>> -- Take Mark's advice to use prefix "dio-" to distinguish dio orphan
>>entry from unlink/rename.
>> -- Take Mark's advice to treat this feature as a ro compat feature.
>> -- Fix a bug in case of not cluster aligned io, cluster_align should
>>be !zero_len, not !!zero_len.
>> -- Fix a bug in case of fallocate with FALLOC_FL_KEEP_SIZE.
>> -- Fix the wrong *ppos and written when completing the rest request
>>using buffer io.
>>
>> Corresponding ocfs2 tools (mkfs.ocfs2, tunefs.ocfs2, fsck.ocfs2, etc.)
>> will be updated later.
>>
>>
>> ___
>> Ocfs2-devel mailing list
>> Ocfs2-devel@oss.oracle.com
>> https://oss.oracle.com/mailman/listinfo/ocfs2-devel
>>
> 
> 
> 



___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


[Ocfs2-devel] [PATCH 6/9 v6] ocfs2: do not fallback to buffer I/O write if appending

2015-01-20 Thread Joseph Qi
Now we can do direct io and do not fallback to buffered IO any more in
case of append O_DIRECT write.

Signed-off-by: Joseph Qi 
Cc: Weiwei Wang 
---
 fs/ocfs2/file.c | 5 -
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c
index d0ed2c1..c1446cf 100644
--- a/fs/ocfs2/file.c
+++ b/fs/ocfs2/file.c
@@ -2116,6 +2116,9 @@ static int ocfs2_prepare_inode_for_write(struct file 
*file,
struct dentry *dentry = file->f_path.dentry;
struct inode *inode = dentry->d_inode;
loff_t saved_pos = 0, end;
+   struct ocfs2_super *osb = OCFS2_SB(inode->i_sb);
+   int full_coherency = !(osb->s_mount_opt &
+   OCFS2_MOUNT_COHERENCY_BUFFERED);

/*
 * We start with a read level meta lock and only jump to an ex
@@ -2204,7 +2207,7 @@ static int ocfs2_prepare_inode_for_write(struct file 
*file,
 * one node could wind up truncating another
 * nodes writes.
 */
-   if (end > i_size_read(inode)) {
+   if (end > i_size_read(inode) && !full_coherency) {
*direct_io = 0;
break;
}
-- 
1.8.4.3


___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 07/17] quota: Switch ->get_dqblk() and ->set_dqblk() to use bytes as space units

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:07:20, Christoph Hellwig wrote:
> > diff --git a/fs/xfs/libxfs/xfs_fs.h b/fs/xfs/libxfs/xfs_fs.h
> > index 18dc721ca19f..f718ba1f2ccb 100644
> > --- a/fs/xfs/libxfs/xfs_fs.h
> > +++ b/fs/xfs/libxfs/xfs_fs.h
> > @@ -559,18 +559,4 @@ typedef struct xfs_swapext
> >  /* XFS_IOC_GETFSUUID -- deprecated 140  */
> >  
> >  
> > -#ifndef HAVE_BBMACROS
> > -/*
> > - * Block I/O parameterization. A basic block (BB) is the lowest size of
> > - * filesystem allocation, and must equal 512.  Length units given to bio
> > - * routines are in BB's.
> > - */
> > -#define BBSHIFT9
> > -#define BBSIZE (1< > -#define BBMASK (BBSIZE-1)
> > -#define BTOBB(bytes)   (((__u64)(bytes) + BBSIZE - 1) >> BBSHIFT)
> > -#define BTOBBT(bytes)  ((__u64)(bytes) >> BBSHIFT)
> > -#define BBTOB(bbs) ((bbs) << BBSHIFT)
> > -#endif
> 
> Please don't move these defintions around and just opencode them in
> the quota code.
  I have moved the definitions because Dave asked me to use them in the XFS
parts of quota code (maybe he didn't realize that to be able to use them I
have to move the definitions somewhere where quota code can include them).
Dave? I personally don't care which variant will get used...

> Otherwise looks good:
> 
> Reviewed-by: Christoph Hellwig 
  Thanks.

Honza
-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 02/17] quota: Wire up ->quota_{enable, disable} callbacks into Q_QUOTA{ON, OFF}

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:01:21, Christoph Hellwig wrote:
> On Fri, Jan 16, 2015 at 01:47:36PM +0100, Jan Kara wrote:
> > Make Q_QUOTAON / Q_QUOTAOFF quotactl call ->quota_enable /
> > ->quota_disable callback when provided. To match current behavior of
> > ocfs2 & ext4 we make these quotactls turn on / off quota enforcement for
> > appropriate quota type.
> > 
> > Signed-off-by: Jan Kara 
> > ---
> >  fs/quota/quota.c | 31 +++
> >  include/linux/quotaops.h |  2 ++
> >  2 files changed, 29 insertions(+), 4 deletions(-)
> > 
> > diff --git a/fs/quota/quota.c b/fs/quota/quota.c
> > index 5b307e2b5719..748716ffee48 100644
> > --- a/fs/quota/quota.c
> > +++ b/fs/quota/quota.c
> > @@ -66,18 +66,43 @@ static int quota_sync_all(int type)
> > return ret;
> >  }
> >  
> > +unsigned int qtype_limit_flag(int type)
> > +{
> > +   switch (type) {
> > +   case USRQUOTA:
> > +   return FS_QUOTA_UDQ_ENFD;
> > +   case GRPQUOTA:
> > +   return FS_QUOTA_GDQ_ENFD;
> > +   case PRJQUOTA:
> > +   return FS_QUOTA_PDQ_ENFD;
> > +   }
> > +   return 0;
> 
> 
> What's the limit_ in the name supposed to mean?
  qtype_enforce_flag() explains probably better what's going on so I've
used that instead.

Honza
-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 03/17] quota: Add ->quota_{enable, disable} callbacks for VFS quotas

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:02:48, Christoph Hellwig wrote:
> On Fri, Jan 16, 2015 at 01:47:37PM +0100, Jan Kara wrote:
> > +EXPORT_SYMBOL(dquot_quota_enable);
> 
> > +EXPORT_SYMBOL(dquot_quota_disable);
> 
> I can't find any modular users of this (in fact none outside this
> file), so I'd suggest to keep these local.
  OK, we can do that. I've exported the functions because in principle
filesystems are free to provide own .quota_enable function and then may
want to call dquot_quota_enable() from there but currently nobody needs
that so let's export them only if there are real users.

Honza
-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 05/17] ocfs2: Use generic helpers for quotaon and quotaoff

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:03:47, Christoph Hellwig wrote:
> On Fri, Jan 16, 2015 at 01:47:39PM +0100, Jan Kara wrote:
> > Ocfs2 can just use the generic helpers provided by quota code for
> > turning quotas on and off when quota files are stored as system inodes.
> > The only difference is the feature test in ocfs2_quota_on() and that is
> > covered by dquot_quota_enable() checking whether usage tracking is
> > enabled (which can happen only if the filesystem has the quota feature
> > set).
> > 
> > Signed-off-by: Jan Kara 
> > ---
> >  fs/ocfs2/super.c | 32 +---
> >  1 file changed, 1 insertion(+), 31 deletions(-)
> > 
> > diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c
> > index 83723179e1ec..706c71c2955d 100644
> > --- a/fs/ocfs2/super.c
> > +++ b/fs/ocfs2/super.c
> > @@ -1000,36 +1000,6 @@ static void ocfs2_disable_quotas(struct ocfs2_super 
> > *osb)
> > }
> >  }
> >  
> > -/* Handle quota on quotactl */
> > -static int ocfs2_quota_on(struct super_block *sb, int type, int format_id)
> > -{
> > -   unsigned int feature[OCFS2_MAXQUOTAS] = {
> > -   OCFS2_FEATURE_RO_COMPAT_USRQUOTA,
> > -   OCFS2_FEATURE_RO_COMPAT_GRPQUOTA};
> > -
> > -   if (!OCFS2_HAS_RO_COMPAT_FEATURE(sb, feature[type]))
> > -   return -EINVAL;
> 
> Where are we doing this feature check now?
  So OCFS2 (similarly as ext4 or xfs) has to enable quota accounting on
mount and at that point we test for the feature. Q_QUOTAON quotactl is
used just to turn on enforcement and at that point it makes no sense to
check for the feature (BTW, the changelog already explains this ;).

Honza
-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 09/17] quota: Make Q_XQUOTASYNC support VFS quota syncing

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:09:14, Christoph Hellwig wrote:
> On Fri, Jan 16, 2015 at 01:47:43PM +0100, Jan Kara wrote:
> > Call ->quota_sync method from Q_XQUOTASYNC for better userspace
> > compatibility.
> 
> Q_XQUOTASYNC never did the equivalent to ->quota_sync, but rather was
> the equivalent to sys_syncfs which also happens to write out quotas.
> 
> Unless you have a really strong reason for wiring it up, I'd rather keep
> it as-is.
  OK, patch dropped.

Honza
-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel


Re: [Ocfs2-devel] [PATCH 12/17] xfs: Convert to using ->get_state callback

2015-01-20 Thread Jan Kara
On Mon 19-01-15 01:38:10, Christoph Hellwig wrote:
> > +static void xfs_qm_fill_state(struct qc_type_state *tstate,
> 
> Normal xfs style would be to keep the "static void " on a separate line,
> as well as the arguments, e.g.
  OK, will change it to conform to the XFS coding style.

> static void
> xfs_qm_fill_state(
>   struct qc_type_state*tstate,
> 
> >
> > + struct xfs_mount *mp,
> > + struct xfs_inode *ip,
> > + xfs_ino_t ino)
> 
> No need to pass mp, as it can be derived as ip->i_mount.
  Good point.

> Btw, I think this code should move into xfs_quotaops.c now
> that it ties into the Linux quota interface, and xfs_qm_scall_getstate
> should be folded into xfs_fs_get_quota_state.
  OK, will do.

Honza

-- 
Jan Kara 
SUSE Labs, CR

___
Ocfs2-devel mailing list
Ocfs2-devel@oss.oracle.com
https://oss.oracle.com/mailman/listinfo/ocfs2-devel