[Ocfs2-commits] mfasheh commits r1638 - in branches/dlm-glue: . src
svn-commits at oss.oracle.com
svn-commits at oss.oracle.com
Wed Nov 10 16:42:07 CST 2004
Author: mfasheh
Date: 2004-11-10 16:42:06 -0600 (Wed, 10 Nov 2004)
New Revision: 1638
Modified:
branches/dlm-glue/configure.in
branches/dlm-glue/src/24io.c
branches/dlm-glue/src/file.c
branches/dlm-glue/src/inode.h
Log:
* bring the dlm-glue branch up to date with trunk, r1622
Modified: branches/dlm-glue/configure.in
===================================================================
--- branches/dlm-glue/configure.in 2004-11-10 22:35:45 UTC (rev 1637)
+++ branches/dlm-glue/configure.in 2004-11-10 22:42:06 UTC (rev 1638)
@@ -252,7 +252,7 @@
if test "x$OCFS_AIO" = "xyes"; then
if test "x$KERNEL_26" = "xyes"; then
have_aio=yes
- elif egrep "EXPORT_SYMBOL.*\(brw_kvec_async\);" "$kernelsrc/kernel/ksyms.c" "$kernelsrc/fs/buffer.c" >/dev/null 2>&1; then
+ elif egrep "EXPORT_SYMBOL.*\(aio_complete\);" "$kerneldir/fs/aio.c" >/dev/null 2>&1; then
have_aio=yes
else
have_aio=no
Modified: branches/dlm-glue/src/24io.c
===================================================================
--- branches/dlm-glue/src/24io.c 2004-11-10 22:35:45 UTC (rev 1637)
+++ branches/dlm-glue/src/24io.c 2004-11-10 22:42:06 UTC (rev 1638)
@@ -352,115 +352,167 @@
} /* ocfs_rw_direct */
#ifdef AIO_ENABLED
-static int ocfs_kvec_rw(struct file *filp, int rw, kvec_cb_t cb,
- size_t size, loff_t pos)
+static void ocfs_aio_issue(void * _iocb);
+
+static void ocfs_aio_complete(struct kiocb *iocb, long res) {
+
+ if (iocb->nr_transferred)
+ res = iocb->nr_transferred;
+
+ aio_complete(iocb, res, 0);
+}
+
+static void ocfs_aio_complete_rw(int rw, void *_iocb, struct kvec *vec,
+ ssize_t res)
{
- int err = 0;
- int max_sectors = 25000;
- struct inode *inode = filp->f_dentry->d_inode;
- unsigned long blocknr, blocks, iosize,myiosize;
- long firstphys;
- int clustersize;
- unsigned long blocks_end_cluster = 0;
-
+ struct kiocb *iocb = _iocb;
+
+ unmap_kvec(vec, rw == READ);
+ free_kvec(vec);
+
+ if (res <= 0)
+ ocfs_aio_complete(iocb, res);
+
+ iocb->nr_transferred += res;
+
+ if ((res != iocb->this_size) || iocb->ctx->dead ||
+ (iocb->nr_transferred == iocb->size)) {
+ ocfs_aio_complete(iocb, 0);
+ return;
+ }
+
+ iocb->this_size = rw;
+ INIT_TQUEUE(&iocb->u.tq, ocfs_aio_issue, iocb);
+ schedule_task(&iocb->u.tq);
+}
+
+static void ocfs_aio_complete_read(void *_iocb, struct kvec *vec, ssize_t res)
+{
+ ocfs_aio_complete_rw(READ, _iocb, vec, res);
+}
+static void ocfs_aio_complete_write(void *_iocb, struct kvec *vec, ssize_t res)
+{
+ ocfs_aio_complete_rw(WRITE, _iocb, vec, res);
+}
+
+static void ocfs_aio_issue(void *_iocb)
+{
+ struct kiocb *iocb = _iocb;
+ struct inode *inode = iocb->filp->f_dentry->d_inode;
+ unsigned long blocknr, blocks, iosize, this, aio_max_blocks;
+ int rc = 0, rw = iocb->this_size;
+ long firstphys, phys;
+ kvec_cb_t cb;
+
/* FIXME: Need to differentiate betwen sectors and blocksize */
int sector_bits = OCFS_SB(inode->i_sb)->s_sectsize_bits;
- int sector_size = 1 << OCFS_SB(inode->i_sb)->s_sectsize_bits;
- int sector_mask = sector_size - 1;
+ int clustersize = inode->i_blksize >> sector_bits;
- unsigned long firstlogic;
- long nextphys;
- unsigned long nextlogic = 0;
- unsigned long totalioblocks = 0;
+ iocb->this_size = 0;
- if (!size || (pos == inode->i_size)) {
- cb.fn(cb.data, cb.vec, err);
- return err;
- }
+ iosize = (iocb->size - iocb->nr_transferred) >> sector_bits;
+ BUG_ON(iosize == 0);
+ blocknr = (iocb->pos + iocb->nr_transferred) >> sector_bits;
+ firstphys = 0;
+ blocks = 0;
- err = -ENXIO;
- if (pos >= inode->i_size) {
- return err;
- }
+ aio_max_blocks = aio_max_size >> sector_bits;
- err = -EINVAL;
- if ((pos < 0) || (pos & sector_mask) || (size & sector_mask)) {
- return err;
+ while (iosize > 0 && blocks < aio_max_blocks) {
+ rc = ocfs_get_sector(inode, blocknr, &phys);
+ if (rc < 0)
+ goto out;
+
+ if (firstphys == 0)
+ firstphys = phys;
+
+ /* issue the io when it stops being contiguous */
+ if (firstphys + blocks != phys)
+ break;
+
+ /* clamp when the rest of the io fits in the cluster */
+ this = min(clustersize - (blocknr % clustersize), iosize);
+ this = min(this, aio_max_blocks - blocks);
+
+ blocks += this;
+ blocknr += this;
+ iosize -= this;
}
- blocknr = pos >> sector_bits;
+ /* we either got the first phys or returned an error from getblock */
+ BUG_ON(blocks == 0);
- blocks = size >> sector_bits;;
- if (blocks > max_sectors)
- blocks = max_sectors;
- if (!blocks) {
- err = -ENXIO;
- return err;
+ iocb->this_size = blocks << sector_bits;
+
+ cb.fn = (rw == READ) ? ocfs_aio_complete_read :
+ ocfs_aio_complete_write;
+ cb.data = iocb;
+ cb.vec = mm_map_user_kvec(iocb->ctx->mm, rw,
+ iocb->buf + iocb->nr_transferred,
+ iocb->this_size);
+ if (unlikely(IS_ERR(cb.vec))) {
+ rc = PTR_ERR(cb.vec);
+ goto out;
}
- iosize = blocks << sector_bits;
- clustersize = inode->i_blksize >> sector_bits;
- blocks_end_cluster = clustersize - (blocknr % clustersize);
- myiosize = size >> sector_bits;
- firstlogic = blocknr;
- totalioblocks = 0;
+ rc = brw_kvec_async(rw, cb, inode->i_dev, blocks, firstphys,
+ sector_bits);
+out:
+ if (rc)
+ ocfs_aio_complete(iocb, rc);
+}
- err = ocfs_get_sector(inode, blocknr, &firstphys);
- if (err)
- return err;
+static ssize_t ocfs_aio_rw(int rw, struct file *file, struct kiocb *req,
+ struct iocb *iocb)
+{
+ struct inode *inode = req->filp->f_dentry->d_inode;
+ loff_t pos = req->pos;
+ size_t size = req->size;
- if (blocks_end_cluster + 1 > myiosize) {
- totalioblocks += myiosize;
- myiosize = 0;
- goto doio;
- } else {
- totalioblocks += blocks_end_cluster;
- myiosize -= blocks_end_cluster;
- nextlogic = firstlogic + blocks_end_cluster;
- }
-again:
- err = ocfs_get_sector(inode, nextlogic, &nextphys);
- if (err)
- return err;
+ int sector_size = 1 << OCFS_SB(inode->i_sb)->s_sectsize_bits;
+ int sector_mask = (1 << sector_size) - 1;
- if (nextphys == (firstphys + totalioblocks)) {
- blocks_end_cluster = clustersize - (nextlogic % clustersize);
- if (blocks_end_cluster + 1 > myiosize) {
- totalioblocks += myiosize;
- myiosize = 0;
- } else {
- totalioblocks += blocks_end_cluster;
- myiosize -= blocks_end_cluster;
- nextlogic = nextlogic + blocks_end_cluster;
- goto again;
- }
- }
-doio:
- blocks = totalioblocks;
- err = brw_kvec_async(rw, cb, inode->i_dev, blocks, firstphys, sector_bits);
- return err;
+ if (!size || (pos == inode->i_size)) {
+ ocfs_aio_complete(req, 0);
+ return 0;
+ }
+
+ if (aio_max_size < sector_size)
+ return -EINVAL;
+ if (pos >= inode->i_size)
+ return -ENXIO;
+
+ if ((pos < 0) || (pos & sector_mask) || (size & sector_mask))
+ return -EINVAL;
+
+ req->nr_transferred = 0;
+
+ /* from this point on errors are communicated through completion */
+ req->this_size = rw;
+ ocfs_aio_issue(req);
+ return 0;
}
-int ocfs_kvec_read(struct file *file, kvec_cb_t cb, size_t size, loff_t pos)
+int ocfs_aio_read(struct file *file, struct kiocb *req, struct iocb *iocb)
{
int ret;
LOG_SET_CONTEXT(KVEC_READ);
- ret = ocfs_kvec_rw(file, READ, cb, size, pos);
+ ret = ocfs_aio_rw(READ, file, req, iocb);
LOG_CLEAR_CONTEXT();
return ret;
}
-int ocfs_kvec_write(struct file *file, kvec_cb_t cb, size_t size, loff_t pos)
+int ocfs_aio_write(struct file *file, struct kiocb *req, struct iocb *iocb)
{
int ret;
LOG_SET_CONTEXT(KVEC_WRITE);
- ret = ocfs_kvec_rw(file, WRITE, cb, size, pos);
+ ret = ocfs_aio_rw(WRITE, file, req, iocb);
LOG_CLEAR_CONTEXT();
return ret;
Modified: branches/dlm-glue/src/file.c
===================================================================
--- branches/dlm-glue/src/file.c 2004-11-10 22:35:45 UTC (rev 1637)
+++ branches/dlm-glue/src/file.c 2004-11-10 22:42:06 UTC (rev 1638)
@@ -534,13 +534,13 @@
.release = ocfs_file_release,
.open = ocfs_file_open,
.ioctl = ocfs_ioctl,
-#if defined(AIO_ENABLED) || defined(AIO_26_ENABLED)
+#if defined(AIO_26_ENABLED)
.aio_read = generic_file_aio_read,
.aio_write = generic_file_aio_write,
-#ifdef AIO_ENABLED
- .kvec_read = ocfs_kvec_read,
- .kvec_write = ocfs_kvec_write,
#endif
+#if defined(AIO_ENABLED)
+ .aio_read = ocfs_aio_read,
+ .aio_write = ocfs_aio_write,
#endif
};
Modified: branches/dlm-glue/src/inode.h
===================================================================
--- branches/dlm-glue/src/inode.h 2004-11-10 22:35:45 UTC (rev 1637)
+++ branches/dlm-glue/src/inode.h 2004-11-10 22:42:06 UTC (rev 1638)
@@ -47,8 +47,8 @@
struct inode *inode,
struct buffer_head *bh);
#ifdef AIO_ENABLED
-int ocfs_kvec_read(struct file *file, kvec_cb_t cb, size_t size, loff_t pos);
-int ocfs_kvec_write(struct file *file, kvec_cb_t cb, size_t size, loff_t pos);
+int ocfs_aio_read(struct file *file, struct kiocb *req, struct iocb *iocb);
+int ocfs_aio_write(struct file *file, struct kiocb *req, struct iocb *iocb);
#endif
#endif /* OCFS2_INODE_H */
More information about the Ocfs2-commits
mailing list