if (fd && (fd->fd_flags & LL_FILE_IGNORE_LOCK))
RETURN(0);
- /* server-side locking for dio unless LL_FILE_LOCKED_DIRECTIO */
+ /* The semantics here is a bit complicated due to compatibility.
+ * The user may be aware of per-file LL_FILE_LOCKED_DIRECTIO,
+ * but not of per-client lockless_direct_io, so the file bit takes
+ * precedence if it is set. If the file bit is not set, we use
+ * lockless I/O unless per-client lockless_direct_io is set to zero.
+ */
+ CLASSERT(SBI_DEFAULT_LOCKLESS_DIRECT_IO == 1);
if ((file->f_flags & O_DIRECT) &&
- !(fd && (fd->fd_flags & LL_FILE_LOCKED_DIRECTIO)))
+ !(fd && (fd->fd_flags & LL_FILE_LOCKED_DIRECTIO)) &&
+ sbi->ll_lockless_direct_io)
RETURN(1);
/* server-side locking for cached I/O with LL_FILE_LOCKLESS_IO */
#define SBI_DEFAULT_LOCKLESS_TRUNCATE_ENABLE 0 /* see bug 23175 */
/* default value for ll_direct_io_default */
#define SBI_DEFAULT_DIRECT_IO_DEFAULT 0
+#define SBI_DEFAULT_LOCKLESS_DIRECT_IO 1
/* percpu data structure for lustre lru page list */
struct ll_pglist_data {
unsigned ll_contention_time; /* seconds */
unsigned ll_lockless_truncate_enable; /* true/false */
+ unsigned ll_lockless_direct_io; /* true/false */
unsigned ll_direct_io_default; /* true/false */
struct ll_ra_info ll_ra_info;
SBI_DEFAULT_READAHEAD_WHOLE_MAX;
sbi->ll_contention_time = SBI_DEFAULT_CONTENTION_SECONDS;
sbi->ll_lockless_truncate_enable = SBI_DEFAULT_LOCKLESS_TRUNCATE_ENABLE;
+ sbi->ll_lockless_direct_io = SBI_DEFAULT_LOCKLESS_DIRECT_IO;
sbi->ll_direct_io_default = SBI_DEFAULT_DIRECT_IO_DEFAULT;
INIT_LIST_HEAD(&sbi->ll_conn_chain);
INIT_LIST_HEAD(&sbi->ll_orphan_dentry_list);
?: count;
}
+static int ll_rd_lockless_direct_io(char *page, char **start, off_t off,
+ int count, int *eof, void *data)
+{
+ struct super_block *sb = data;
+
+ *eof = 1;
+ return snprintf(page, count, "%u\n",
+ ll_s2sbi(sb)->ll_lockless_direct_io);
+}
+
+static int ll_wr_lockless_direct_io(struct file *file, const char *buffer,
+ unsigned long count, void *data)
+{
+ struct super_block *sb = data;
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+
+ return lprocfs_write_helper(buffer, count,
+ &sbi->ll_lockless_direct_io)
+ ?: count;
+}
+
static int ll_rd_statahead_max(char *page, char **start, off_t off,
int count, int *eof, void *data)
{
ll_wr_contention_time, 0},
{ "lockless_truncate", ll_rd_lockless_truncate,
ll_wr_lockless_truncate, 0},
+ { "lockless_direct_io", ll_rd_lockless_direct_io,
+ ll_wr_lockless_direct_io, 0},
{ "direct_io_default", ll_rd_direct_io_default,
ll_wr_direct_io_default, 0},
{ "statahead_max", ll_rd_statahead_max, ll_wr_statahead_max, 0 },