From 1cb77a4a765581b3bee1e227089584e711b9500a Mon Sep 17 00:00:00 2001
From: zhaoyifeng <zyf@ubuntu-fs.(none)>
Date: Fri, 21 Jan 2011 18:03:02 +0800
Subject: [PATCH] support 4GB disk.

---
 drivers/mtd/mtd_blkdevs.c    | 28 ++++++++++++++++++++++------
 drivers/mtd/mtdblock.c       |  8 ++++----
 drivers/mtd/mtdblock_ro.c    |  8 ++++----
 include/linux/mtd/blktrans.h |  4 ++--
 4 files changed, 32 insertions(+), 16 deletions(-)
 mode change 100644 => 100755 drivers/mtd/mtd_blkdevs.c
 mode change 100644 => 100755 drivers/mtd/mtdblock.c
 mode change 100644 => 100755 include/linux/mtd/blktrans.h

diff --git a/drivers/mtd/mtd_blkdevs.c b/drivers/mtd/mtd_blkdevs.c
old mode 100644
new mode 100755
index 8ca17a3e96ea..4c1ded5a9ce7
--- a/drivers/mtd/mtd_blkdevs.c
+++ b/drivers/mtd/mtd_blkdevs.c
@@ -38,9 +38,24 @@ static int do_blktrans_request(struct mtd_blktrans_ops *tr,
 {
 	unsigned long block, nsect;
 	char *buf;
-
+#if 0
 	block = blk_rq_pos(req) << 9 >> tr->blkshift;
 	nsect = blk_rq_cur_bytes(req) >> tr->blkshift;
+#else  //modify by zyf for cap>=4GB 20110120
+	block = blk_rq_pos(req);
+	nsect = blk_rq_cur_bytes(req) >> tr->blkshift;
+    if(tr->blkshift != 9)
+    {
+        if(tr->blkshift > 9)
+        {
+    	    block = blk_rq_pos(req) >> (tr->blkshift - 9);
+        }
+        else
+        {
+	        block = blk_rq_pos(req) << (9 - tr->blkshift);
+        }
+    }
+#endif
 
 	buf = req->buffer;
 
@@ -56,8 +71,8 @@ static int do_blktrans_request(struct mtd_blktrans_ops *tr,
 
 	switch(rq_data_dir(req)) {
 	case READ:
-		for (; nsect > 0; nsect--, block++, buf += tr->blksize)
-			if (tr->readsect(dev, block, buf))
+		//for (; nsect > 0; nsect--, block++, buf += tr->blksize)
+			if (tr->readsect(dev, block,nsect, buf))
 				return -EIO;
 		return 0;
 
@@ -65,8 +80,8 @@ static int do_blktrans_request(struct mtd_blktrans_ops *tr,
 		if (!tr->writesect)
 			return -EIO;
 
-		for (; nsect > 0; nsect--, block++, buf += tr->blksize)
-			if (tr->writesect(dev, block, buf))
+		//for (; nsect > 0; nsect--, block++, buf += tr->blksize)
+			if (tr->writesect(dev, block,nsect, buf))
 				return -EIO;
 		return 0;
 
@@ -277,7 +292,8 @@ int add_mtd_blktrans_dev(struct mtd_blktrans_dev *new)
 
 	/* 2.5 has capacity in units of 512 bytes while still
 	   having BLOCK_SIZE_BITS set to 10. Just to keep us amused. */
-	set_capacity(gd, (new->size * tr->blksize) >> 9);
+	//set_capacity(gd, (new->size * tr->blksize) >> 9);
+	set_capacity(gd, (new->size >> 9) * tr->blksize);   //modify by zyf for cap>=4GB 20110120
 
 	gd->private_data = new;
 	new->blkcore_priv = gd;
diff --git a/drivers/mtd/mtdblock.c b/drivers/mtd/mtdblock.c
old mode 100644
new mode 100755
index 9f41b1a853c1..3a5653a3c002
--- a/drivers/mtd/mtdblock.c
+++ b/drivers/mtd/mtdblock.c
@@ -242,14 +242,14 @@ static int do_cached_read (struct mtdblk_dev *mtdblk, unsigned long pos,
 }
 
 static int mtdblock_readsect(struct mtd_blktrans_dev *dev,
-			      unsigned long block, char *buf)
+			      unsigned long block,unsigned long nsect, char *buf)
 {
 	struct mtdblk_dev *mtdblk = mtdblks[dev->devnum];
-	return do_cached_read(mtdblk, block<<9, 512, buf);
+	return do_cached_read(mtdblk, block<<9, 512*nsect, buf);
 }
 
 static int mtdblock_writesect(struct mtd_blktrans_dev *dev,
-			      unsigned long block, char *buf)
+			      unsigned long block,unsigned long nsect, char *buf)
 {
 	struct mtdblk_dev *mtdblk = mtdblks[dev->devnum];
 	if (unlikely(!mtdblk->cache_data && mtdblk->cache_size)) {
@@ -261,7 +261,7 @@ static int mtdblock_writesect(struct mtd_blktrans_dev *dev,
 		 * return -EAGAIN sometimes, but why bother?
 		 */
 	}
-	return do_cached_write(mtdblk, block<<9, 512, buf);
+	return do_cached_write(mtdblk, block<<9, 512*nsect, buf);
 }
 
 static int mtdblock_open(struct mtd_blktrans_dev *mbd)
diff --git a/drivers/mtd/mtdblock_ro.c b/drivers/mtd/mtdblock_ro.c
index 852165f8b1c3..f807b2c08bb0 100644
--- a/drivers/mtd/mtdblock_ro.c
+++ b/drivers/mtd/mtdblock_ro.c
@@ -10,21 +10,21 @@
 #include <linux/mtd/blktrans.h>
 
 static int mtdblock_readsect(struct mtd_blktrans_dev *dev,
-			      unsigned long block, char *buf)
+			      unsigned long block, unsigned long nsect, char *buf)
 {
 	size_t retlen;
 
-	if (dev->mtd->read(dev->mtd, (block * 512), 512, &retlen, buf))
+	if (dev->mtd->read(dev->mtd, (block * 512), 512*nsect, &retlen, buf))
 		return 1;
 	return 0;
 }
 
 static int mtdblock_writesect(struct mtd_blktrans_dev *dev,
-			      unsigned long block, char *buf)
+			      unsigned long block, unsigned long nsect, char *buf)
 {
 	size_t retlen;
 
-	if (dev->mtd->write(dev->mtd, (block * 512), 512, &retlen, buf))
+	if (dev->mtd->write(dev->mtd, (block * 512), 512*nsect, &retlen, buf))
 		return 1;
 	return 0;
 }
diff --git a/include/linux/mtd/blktrans.h b/include/linux/mtd/blktrans.h
old mode 100644
new mode 100755
index 8b4aa0523db7..2e0ef53f4a3a
--- a/include/linux/mtd/blktrans.h
+++ b/include/linux/mtd/blktrans.h
@@ -38,9 +38,9 @@ struct mtd_blktrans_ops {
 
 	/* Access functions */
 	int (*readsect)(struct mtd_blktrans_dev *dev,
-		    unsigned long block, char *buffer);
+		    unsigned long block,unsigned long nsect, char *buffer);
 	int (*writesect)(struct mtd_blktrans_dev *dev,
-		     unsigned long block, char *buffer);
+		     unsigned long block,unsigned long nsect, char *buffer);
 	int (*discard)(struct mtd_blktrans_dev *dev,
 		       unsigned long block, unsigned nr_blocks);
 
-- 
2.34.1