]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - drivers/mtd/onenand/onenand_base.c
[MTD] OneNAND: fix onenand_wait bug
[linux-2.6-omap-h63xx.git] / drivers / mtd / onenand / onenand_base.c
index fc84ddc4987f82d40ea4d723d1d5f25c3bb92dbe..3fab4d1b68bd8da3398bf35866f1f8006843897d 100644 (file)
@@ -318,15 +318,10 @@ static int onenand_wait(struct mtd_info *mtd, int state)
        ctrl = this->read_word(this->base + ONENAND_REG_CTRL_STATUS);
 
        if (ctrl & ONENAND_CTRL_ERROR) {
-               /* It maybe occur at initial bad block */
                DEBUG(MTD_DEBUG_LEVEL0, "onenand_wait: controller error = 0x%04x\n", ctrl);
-               /* Clear other interrupt bits for preventing ECC error */
-               interrupt &= ONENAND_INT_MASTER;
-       }
-
-       if (ctrl & ONENAND_CTRL_LOCK) {
-               DEBUG(MTD_DEBUG_LEVEL0, "onenand_wait: it's locked error = 0x%04x\n", ctrl);
-               return -EACCES;
+               if (ctrl & ONENAND_CTRL_LOCK)
+                       DEBUG(MTD_DEBUG_LEVEL0, "onenand_wait: it's locked error.\n");
+               return ctrl;
        }
 
        if (interrupt & ONENAND_INT_READ) {
@@ -406,7 +401,7 @@ static int onenand_try_interrupt_wait(struct mtd_info *mtd, int state)
 
                /* Release the irq */
                free_irq(this->irq, this);
-               
+
                this->wait = onenand_wait;
        }
 
@@ -750,21 +745,21 @@ static int onenand_read(struct mtd_info *mtd, loff_t from, size_t len,
 
                        ret = this->wait(mtd, FL_READING);
                        /* First copy data and check return value for ECC handling */
-                       onenand_update_bufferram(mtd, from, 1);
+                       onenand_update_bufferram(mtd, from, !ret);
                }
 
                this->read_bufferram(mtd, ONENAND_DATARAM, buf, column, thislen);
 
-               read += thislen;
-
-               if (read == len)
-                       break;
-
                if (ret) {
                        DEBUG(MTD_DEBUG_LEVEL0, "onenand_read: read failed = %d\n", ret);
                        goto out;
                }
 
+               read += thislen;
+
+               if (read == len)
+                       break;
+
                from += thislen;
                buf += thislen;
        }
@@ -832,16 +827,16 @@ int onenand_do_read_oob(struct mtd_info *mtd, loff_t from, size_t len,
 
                this->read_bufferram(mtd, ONENAND_SPARERAM, buf, column, thislen);
 
+               if (ret) {
+                       DEBUG(MTD_DEBUG_LEVEL0, "onenand_read_oob: read failed = 0x%x\n", ret);
+                       goto out;
+               }
+
                read += thislen;
 
                if (read == len)
                        break;
 
-               if (ret) {
-                       DEBUG(MTD_DEBUG_LEVEL0, "onenand_read_oob: read failed = %d\n", ret);
-                       goto out;
-               }
-
                buf += thislen;
 
                /* Read more? */
@@ -871,8 +866,8 @@ static int onenand_read_oob(struct mtd_info *mtd, loff_t from,
 {
        BUG_ON(ops->mode != MTD_OOB_PLACE);
 
-       return onenand_do_read_oob(mtd, from + ops->ooboffs, ops->len,
-                                  &ops->retlen, ops->oobbuf);
+       return onenand_do_read_oob(mtd, from + ops->ooboffs, ops->ooblen,
+                                  &ops->oobretlen, ops->oobbuf);
 }
 
 #ifdef CONFIG_MTD_ONENAND_VERIFY_WRITE
@@ -1114,8 +1109,8 @@ static int onenand_write_oob(struct mtd_info *mtd, loff_t to,
 {
        BUG_ON(ops->mode != MTD_OOB_PLACE);
 
-       return onenand_do_write_oob(mtd, to + ops->ooboffs, ops->len,
-                                   &ops->retlen, ops->oobbuf);
+       return onenand_do_write_oob(mtd, to + ops->ooboffs, ops->ooblen,
+                                   &ops->oobretlen, ops->oobbuf);
 }
 
 /**
@@ -1199,10 +1194,7 @@ static int onenand_erase(struct mtd_info *mtd, struct erase_info *instr)
                ret = this->wait(mtd, FL_ERASING);
                /* Check, if it is write protected */
                if (ret) {
-                       if (ret == -EPERM)
-                               DEBUG(MTD_DEBUG_LEVEL0, "onenand_erase: Device is write protected!!!\n");
-                       else
-                               DEBUG(MTD_DEBUG_LEVEL0, "onenand_erase: Failed erase, block %d\n", (unsigned) (addr >> this->erase_shift));
+                       DEBUG(MTD_DEBUG_LEVEL0, "onenand_erase: Failed erase, block %d\n", (unsigned) (addr >> this->erase_shift));
                        instr->state = MTD_ERASE_FAILED;
                        instr->fail_addr = addr;
                        goto erase_exit;