qemu/hw/block/nand.c
<<
>>
Prefs
   1/*
   2 * Flash NAND memory emulation.  Based on "16M x 8 Bit NAND Flash
   3 * Memory" datasheet for the KM29U128AT / K9F2808U0A chips from
   4 * Samsung Electronic.
   5 *
   6 * Copyright (c) 2006 Openedhand Ltd.
   7 * Written by Andrzej Zaborowski <balrog@zabor.org>
   8 *
   9 * Support for additional features based on "MT29F2G16ABCWP 2Gx16"
  10 * datasheet from Micron Technology and "NAND02G-B2C" datasheet
  11 * from ST Microelectronics.
  12 *
  13 * This code is licensed under the GNU GPL v2.
  14 *
  15 * Contributions after 2012-01-13 are licensed under the terms of the
  16 * GNU GPL, version 2 or (at your option) any later version.
  17 */
  18
  19#ifndef NAND_IO
  20
  21#include "qemu/osdep.h"
  22#include "hw/hw.h"
  23#include "hw/qdev-properties.h"
  24#include "hw/qdev-properties-system.h"
  25#include "hw/block/flash.h"
  26#include "sysemu/block-backend.h"
  27#include "migration/vmstate.h"
  28#include "qapi/error.h"
  29#include "qemu/error-report.h"
  30#include "qemu/module.h"
  31#include "qom/object.h"
  32
  33# define NAND_CMD_READ0         0x00
  34# define NAND_CMD_READ1         0x01
  35# define NAND_CMD_READ2         0x50
  36# define NAND_CMD_LPREAD2       0x30
  37# define NAND_CMD_NOSERIALREAD2 0x35
  38# define NAND_CMD_RANDOMREAD1   0x05
  39# define NAND_CMD_RANDOMREAD2   0xe0
  40# define NAND_CMD_READID        0x90
  41# define NAND_CMD_RESET         0xff
  42# define NAND_CMD_PAGEPROGRAM1  0x80
  43# define NAND_CMD_PAGEPROGRAM2  0x10
  44# define NAND_CMD_CACHEPROGRAM2 0x15
  45# define NAND_CMD_BLOCKERASE1   0x60
  46# define NAND_CMD_BLOCKERASE2   0xd0
  47# define NAND_CMD_READSTATUS    0x70
  48# define NAND_CMD_COPYBACKPRG1  0x85
  49
  50# define NAND_IOSTATUS_ERROR    (1 << 0)
  51# define NAND_IOSTATUS_PLANE0   (1 << 1)
  52# define NAND_IOSTATUS_PLANE1   (1 << 2)
  53# define NAND_IOSTATUS_PLANE2   (1 << 3)
  54# define NAND_IOSTATUS_PLANE3   (1 << 4)
  55# define NAND_IOSTATUS_READY    (1 << 6)
  56# define NAND_IOSTATUS_UNPROTCT (1 << 7)
  57
  58# define MAX_PAGE               0x800
  59# define MAX_OOB                0x40
  60
  61typedef struct NANDFlashState NANDFlashState;
  62struct NANDFlashState {
  63    DeviceState parent_obj;
  64
  65    uint8_t manf_id, chip_id;
  66    uint8_t buswidth; /* in BYTES */
  67    int size, pages;
  68    int page_shift, oob_shift, erase_shift, addr_shift;
  69    uint8_t *storage;
  70    BlockBackend *blk;
  71    int mem_oob;
  72
  73    uint8_t cle, ale, ce, wp, gnd;
  74
  75    uint8_t io[MAX_PAGE + MAX_OOB + 0x400];
  76    uint8_t *ioaddr;
  77    int iolen;
  78
  79    uint32_t cmd;
  80    uint64_t addr;
  81    int addrlen;
  82    int status;
  83    int offset;
  84
  85    void (*blk_write)(NANDFlashState *s);
  86    void (*blk_erase)(NANDFlashState *s);
  87    void (*blk_load)(NANDFlashState *s, uint64_t addr, int offset);
  88
  89    uint32_t ioaddr_vmstate;
  90};
  91
  92#define TYPE_NAND "nand"
  93
  94OBJECT_DECLARE_SIMPLE_TYPE(NANDFlashState, NAND)
  95
  96static void mem_and(uint8_t *dest, const uint8_t *src, size_t n)
  97{
  98    /* Like memcpy() but we logical-AND the data into the destination */
  99    int i;
 100    for (i = 0; i < n; i++) {
 101        dest[i] &= src[i];
 102    }
 103}
 104
 105# define NAND_NO_AUTOINCR       0x00000001
 106# define NAND_BUSWIDTH_16       0x00000002
 107# define NAND_NO_PADDING        0x00000004
 108# define NAND_CACHEPRG          0x00000008
 109# define NAND_COPYBACK          0x00000010
 110# define NAND_IS_AND            0x00000020
 111# define NAND_4PAGE_ARRAY       0x00000040
 112# define NAND_NO_READRDY        0x00000100
 113# define NAND_SAMSUNG_LP        (NAND_NO_PADDING | NAND_COPYBACK)
 114
 115# define NAND_IO
 116
 117# define PAGE(addr)             ((addr) >> ADDR_SHIFT)
 118# define PAGE_START(page)       (PAGE(page) * (NAND_PAGE_SIZE + OOB_SIZE))
 119# define PAGE_MASK              ((1 << ADDR_SHIFT) - 1)
 120# define OOB_SHIFT              (PAGE_SHIFT - 5)
 121# define OOB_SIZE               (1 << OOB_SHIFT)
 122# define SECTOR(addr)           ((addr) >> (9 + ADDR_SHIFT - PAGE_SHIFT))
 123# define SECTOR_OFFSET(addr)    ((addr) & ((511 >> PAGE_SHIFT) << 8))
 124
 125# define NAND_PAGE_SIZE         256
 126# define PAGE_SHIFT             8
 127# define PAGE_SECTORS           1
 128# define ADDR_SHIFT             8
 129# include "nand.c"
 130# define NAND_PAGE_SIZE         512
 131# define PAGE_SHIFT             9
 132# define PAGE_SECTORS           1
 133# define ADDR_SHIFT             8
 134# include "nand.c"
 135# define NAND_PAGE_SIZE         2048
 136# define PAGE_SHIFT             11
 137# define PAGE_SECTORS           4
 138# define ADDR_SHIFT             16
 139# include "nand.c"
 140
 141/* Information based on Linux drivers/mtd/nand/raw/nand_ids.c */
 142static const struct {
 143    int size;
 144    int width;
 145    int page_shift;
 146    int erase_shift;
 147    uint32_t options;
 148} nand_flash_ids[0x100] = {
 149    [0 ... 0xff] = { 0 },
 150
 151    [0x6b] = { 4,       8,      9, 4, 0 },
 152    [0xe3] = { 4,       8,      9, 4, 0 },
 153    [0xe5] = { 4,       8,      9, 4, 0 },
 154    [0xd6] = { 8,       8,      9, 4, 0 },
 155    [0xe6] = { 8,       8,      9, 4, 0 },
 156
 157    [0x33] = { 16,      8,      9, 5, 0 },
 158    [0x73] = { 16,      8,      9, 5, 0 },
 159    [0x43] = { 16,      16,     9, 5, NAND_BUSWIDTH_16 },
 160    [0x53] = { 16,      16,     9, 5, NAND_BUSWIDTH_16 },
 161
 162    [0x35] = { 32,      8,      9, 5, 0 },
 163    [0x75] = { 32,      8,      9, 5, 0 },
 164    [0x45] = { 32,      16,     9, 5, NAND_BUSWIDTH_16 },
 165    [0x55] = { 32,      16,     9, 5, NAND_BUSWIDTH_16 },
 166
 167    [0x36] = { 64,      8,      9, 5, 0 },
 168    [0x76] = { 64,      8,      9, 5, 0 },
 169    [0x46] = { 64,      16,     9, 5, NAND_BUSWIDTH_16 },
 170    [0x56] = { 64,      16,     9, 5, NAND_BUSWIDTH_16 },
 171
 172    [0x78] = { 128,     8,      9, 5, 0 },
 173    [0x39] = { 128,     8,      9, 5, 0 },
 174    [0x79] = { 128,     8,      9, 5, 0 },
 175    [0x72] = { 128,     16,     9, 5, NAND_BUSWIDTH_16 },
 176    [0x49] = { 128,     16,     9, 5, NAND_BUSWIDTH_16 },
 177    [0x74] = { 128,     16,     9, 5, NAND_BUSWIDTH_16 },
 178    [0x59] = { 128,     16,     9, 5, NAND_BUSWIDTH_16 },
 179
 180    [0x71] = { 256,     8,      9, 5, 0 },
 181
 182    /*
 183     * These are the new chips with large page size. The pagesize and the
 184     * erasesize is determined from the extended id bytes
 185     */
 186# define LP_OPTIONS     (NAND_SAMSUNG_LP | NAND_NO_READRDY | NAND_NO_AUTOINCR)
 187# define LP_OPTIONS16   (LP_OPTIONS | NAND_BUSWIDTH_16)
 188
 189    /* 512 Megabit */
 190    [0xa2] = { 64,      8,      0, 0, LP_OPTIONS },
 191    [0xf2] = { 64,      8,      0, 0, LP_OPTIONS },
 192    [0xb2] = { 64,      16,     0, 0, LP_OPTIONS16 },
 193    [0xc2] = { 64,      16,     0, 0, LP_OPTIONS16 },
 194
 195    /* 1 Gigabit */
 196    [0xa1] = { 128,     8,      0, 0, LP_OPTIONS },
 197    [0xf1] = { 128,     8,      0, 0, LP_OPTIONS },
 198    [0xb1] = { 128,     16,     0, 0, LP_OPTIONS16 },
 199    [0xc1] = { 128,     16,     0, 0, LP_OPTIONS16 },
 200
 201    /* 2 Gigabit */
 202    [0xaa] = { 256,     8,      0, 0, LP_OPTIONS },
 203    [0xda] = { 256,     8,      0, 0, LP_OPTIONS },
 204    [0xba] = { 256,     16,     0, 0, LP_OPTIONS16 },
 205    [0xca] = { 256,     16,     0, 0, LP_OPTIONS16 },
 206
 207    /* 4 Gigabit */
 208    [0xac] = { 512,     8,      0, 0, LP_OPTIONS },
 209    [0xdc] = { 512,     8,      0, 0, LP_OPTIONS },
 210    [0xbc] = { 512,     16,     0, 0, LP_OPTIONS16 },
 211    [0xcc] = { 512,     16,     0, 0, LP_OPTIONS16 },
 212
 213    /* 8 Gigabit */
 214    [0xa3] = { 1024,    8,      0, 0, LP_OPTIONS },
 215    [0xd3] = { 1024,    8,      0, 0, LP_OPTIONS },
 216    [0xb3] = { 1024,    16,     0, 0, LP_OPTIONS16 },
 217    [0xc3] = { 1024,    16,     0, 0, LP_OPTIONS16 },
 218
 219    /* 16 Gigabit */
 220    [0xa5] = { 2048,    8,      0, 0, LP_OPTIONS },
 221    [0xd5] = { 2048,    8,      0, 0, LP_OPTIONS },
 222    [0xb5] = { 2048,    16,     0, 0, LP_OPTIONS16 },
 223    [0xc5] = { 2048,    16,     0, 0, LP_OPTIONS16 },
 224};
 225
 226static void nand_reset(DeviceState *dev)
 227{
 228    NANDFlashState *s = NAND(dev);
 229    s->cmd = NAND_CMD_READ0;
 230    s->addr = 0;
 231    s->addrlen = 0;
 232    s->iolen = 0;
 233    s->offset = 0;
 234    s->status &= NAND_IOSTATUS_UNPROTCT;
 235    s->status |= NAND_IOSTATUS_READY;
 236}
 237
 238static inline void nand_pushio_byte(NANDFlashState *s, uint8_t value)
 239{
 240    s->ioaddr[s->iolen++] = value;
 241    for (value = s->buswidth; --value;) {
 242        s->ioaddr[s->iolen++] = 0;
 243    }
 244}
 245
 246static void nand_command(NANDFlashState *s)
 247{
 248    unsigned int offset;
 249    switch (s->cmd) {
 250    case NAND_CMD_READ0:
 251        s->iolen = 0;
 252        break;
 253
 254    case NAND_CMD_READID:
 255        s->ioaddr = s->io;
 256        s->iolen = 0;
 257        nand_pushio_byte(s, s->manf_id);
 258        nand_pushio_byte(s, s->chip_id);
 259        nand_pushio_byte(s, 'Q'); /* Don't-care byte (often 0xa5) */
 260        if (nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) {
 261            /* Page Size, Block Size, Spare Size; bit 6 indicates
 262             * 8 vs 16 bit width NAND.
 263             */
 264            nand_pushio_byte(s, (s->buswidth == 2) ? 0x55 : 0x15);
 265        } else {
 266            nand_pushio_byte(s, 0xc0); /* Multi-plane */
 267        }
 268        break;
 269
 270    case NAND_CMD_RANDOMREAD2:
 271    case NAND_CMD_NOSERIALREAD2:
 272        if (!(nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP))
 273            break;
 274        offset = s->addr & ((1 << s->addr_shift) - 1);
 275        s->blk_load(s, s->addr, offset);
 276        if (s->gnd)
 277            s->iolen = (1 << s->page_shift) - offset;
 278        else
 279            s->iolen = (1 << s->page_shift) + (1 << s->oob_shift) - offset;
 280        break;
 281
 282    case NAND_CMD_RESET:
 283        nand_reset(DEVICE(s));
 284        break;
 285
 286    case NAND_CMD_PAGEPROGRAM1:
 287        s->ioaddr = s->io;
 288        s->iolen = 0;
 289        break;
 290
 291    case NAND_CMD_PAGEPROGRAM2:
 292        if (s->wp) {
 293            s->blk_write(s);
 294        }
 295        break;
 296
 297    case NAND_CMD_BLOCKERASE1:
 298        break;
 299
 300    case NAND_CMD_BLOCKERASE2:
 301        s->addr &= (1ull << s->addrlen * 8) - 1;
 302        s->addr <<= nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP ?
 303                                                                    16 : 8;
 304
 305        if (s->wp) {
 306            s->blk_erase(s);
 307        }
 308        break;
 309
 310    case NAND_CMD_READSTATUS:
 311        s->ioaddr = s->io;
 312        s->iolen = 0;
 313        nand_pushio_byte(s, s->status);
 314        break;
 315
 316    default:
 317        printf("%s: Unknown NAND command 0x%02x\n", __func__, s->cmd);
 318    }
 319}
 320
 321static int nand_pre_save(void *opaque)
 322{
 323    NANDFlashState *s = NAND(opaque);
 324
 325    s->ioaddr_vmstate = s->ioaddr - s->io;
 326
 327    return 0;
 328}
 329
 330static int nand_post_load(void *opaque, int version_id)
 331{
 332    NANDFlashState *s = NAND(opaque);
 333
 334    if (s->ioaddr_vmstate > sizeof(s->io)) {
 335        return -EINVAL;
 336    }
 337    s->ioaddr = s->io + s->ioaddr_vmstate;
 338
 339    return 0;
 340}
 341
 342static const VMStateDescription vmstate_nand = {
 343    .name = "nand",
 344    .version_id = 1,
 345    .minimum_version_id = 1,
 346    .pre_save = nand_pre_save,
 347    .post_load = nand_post_load,
 348    .fields = (VMStateField[]) {
 349        VMSTATE_UINT8(cle, NANDFlashState),
 350        VMSTATE_UINT8(ale, NANDFlashState),
 351        VMSTATE_UINT8(ce, NANDFlashState),
 352        VMSTATE_UINT8(wp, NANDFlashState),
 353        VMSTATE_UINT8(gnd, NANDFlashState),
 354        VMSTATE_BUFFER(io, NANDFlashState),
 355        VMSTATE_UINT32(ioaddr_vmstate, NANDFlashState),
 356        VMSTATE_INT32(iolen, NANDFlashState),
 357        VMSTATE_UINT32(cmd, NANDFlashState),
 358        VMSTATE_UINT64(addr, NANDFlashState),
 359        VMSTATE_INT32(addrlen, NANDFlashState),
 360        VMSTATE_INT32(status, NANDFlashState),
 361        VMSTATE_INT32(offset, NANDFlashState),
 362        /* XXX: do we want to save s->storage too? */
 363        VMSTATE_END_OF_LIST()
 364    }
 365};
 366
 367static void nand_realize(DeviceState *dev, Error **errp)
 368{
 369    int pagesize;
 370    NANDFlashState *s = NAND(dev);
 371    int ret;
 372
 373
 374    s->buswidth = nand_flash_ids[s->chip_id].width >> 3;
 375    s->size = nand_flash_ids[s->chip_id].size << 20;
 376    if (nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) {
 377        s->page_shift = 11;
 378        s->erase_shift = 6;
 379    } else {
 380        s->page_shift = nand_flash_ids[s->chip_id].page_shift;
 381        s->erase_shift = nand_flash_ids[s->chip_id].erase_shift;
 382    }
 383
 384    switch (1 << s->page_shift) {
 385    case 256:
 386        nand_init_256(s);
 387        break;
 388    case 512:
 389        nand_init_512(s);
 390        break;
 391    case 2048:
 392        nand_init_2048(s);
 393        break;
 394    default:
 395        error_setg(errp, "Unsupported NAND block size %#x",
 396                   1 << s->page_shift);
 397        return;
 398    }
 399
 400    pagesize = 1 << s->oob_shift;
 401    s->mem_oob = 1;
 402    if (s->blk) {
 403        if (!blk_supports_write_perm(s->blk)) {
 404            error_setg(errp, "Can't use a read-only drive");
 405            return;
 406        }
 407        ret = blk_set_perm(s->blk, BLK_PERM_CONSISTENT_READ | BLK_PERM_WRITE,
 408                           BLK_PERM_ALL, errp);
 409        if (ret < 0) {
 410            return;
 411        }
 412        if (blk_getlength(s->blk) >=
 413                (s->pages << s->page_shift) + (s->pages << s->oob_shift)) {
 414            pagesize = 0;
 415            s->mem_oob = 0;
 416        }
 417    } else {
 418        pagesize += 1 << s->page_shift;
 419    }
 420    if (pagesize) {
 421        s->storage = (uint8_t *) memset(g_malloc(s->pages * pagesize),
 422                        0xff, s->pages * pagesize);
 423    }
 424    /* Give s->ioaddr a sane value in case we save state before it is used. */
 425    s->ioaddr = s->io;
 426}
 427
 428static Property nand_properties[] = {
 429    DEFINE_PROP_UINT8("manufacturer_id", NANDFlashState, manf_id, 0),
 430    DEFINE_PROP_UINT8("chip_id", NANDFlashState, chip_id, 0),
 431    DEFINE_PROP_DRIVE("drive", NANDFlashState, blk),
 432    DEFINE_PROP_END_OF_LIST(),
 433};
 434
 435static void nand_class_init(ObjectClass *klass, void *data)
 436{
 437    DeviceClass *dc = DEVICE_CLASS(klass);
 438
 439    dc->realize = nand_realize;
 440    dc->reset = nand_reset;
 441    dc->vmsd = &vmstate_nand;
 442    device_class_set_props(dc, nand_properties);
 443    set_bit(DEVICE_CATEGORY_STORAGE, dc->categories);
 444}
 445
 446static const TypeInfo nand_info = {
 447    .name          = TYPE_NAND,
 448    .parent        = TYPE_DEVICE,
 449    .instance_size = sizeof(NANDFlashState),
 450    .class_init    = nand_class_init,
 451};
 452
 453static void nand_register_types(void)
 454{
 455    type_register_static(&nand_info);
 456}
 457
 458/*
 459 * Chip inputs are CLE, ALE, CE, WP, GND and eight I/O pins.  Chip
 460 * outputs are R/B and eight I/O pins.
 461 *
 462 * CE, WP and R/B are active low.
 463 */
 464void nand_setpins(DeviceState *dev, uint8_t cle, uint8_t ale,
 465                  uint8_t ce, uint8_t wp, uint8_t gnd)
 466{
 467    NANDFlashState *s = NAND(dev);
 468
 469    s->cle = cle;
 470    s->ale = ale;
 471    s->ce = ce;
 472    s->wp = wp;
 473    s->gnd = gnd;
 474    if (wp) {
 475        s->status |= NAND_IOSTATUS_UNPROTCT;
 476    } else {
 477        s->status &= ~NAND_IOSTATUS_UNPROTCT;
 478    }
 479}
 480
 481void nand_getpins(DeviceState *dev, int *rb)
 482{
 483    *rb = 1;
 484}
 485
 486void nand_setio(DeviceState *dev, uint32_t value)
 487{
 488    int i;
 489    NANDFlashState *s = NAND(dev);
 490
 491    if (!s->ce && s->cle) {
 492        if (nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) {
 493            if (s->cmd == NAND_CMD_READ0 && value == NAND_CMD_LPREAD2)
 494                return;
 495            if (value == NAND_CMD_RANDOMREAD1) {
 496                s->addr &= ~((1 << s->addr_shift) - 1);
 497                s->addrlen = 0;
 498                return;
 499            }
 500        }
 501        if (value == NAND_CMD_READ0) {
 502            s->offset = 0;
 503        } else if (value == NAND_CMD_READ1) {
 504            s->offset = 0x100;
 505            value = NAND_CMD_READ0;
 506        } else if (value == NAND_CMD_READ2) {
 507            s->offset = 1 << s->page_shift;
 508            value = NAND_CMD_READ0;
 509        }
 510
 511        s->cmd = value;
 512
 513        if (s->cmd == NAND_CMD_READSTATUS ||
 514                s->cmd == NAND_CMD_PAGEPROGRAM2 ||
 515                s->cmd == NAND_CMD_BLOCKERASE1 ||
 516                s->cmd == NAND_CMD_BLOCKERASE2 ||
 517                s->cmd == NAND_CMD_NOSERIALREAD2 ||
 518                s->cmd == NAND_CMD_RANDOMREAD2 ||
 519                s->cmd == NAND_CMD_RESET) {
 520            nand_command(s);
 521        }
 522
 523        if (s->cmd != NAND_CMD_RANDOMREAD2) {
 524            s->addrlen = 0;
 525        }
 526    }
 527
 528    if (s->ale) {
 529        unsigned int shift = s->addrlen * 8;
 530        uint64_t mask = ~(0xffull << shift);
 531        uint64_t v = (uint64_t)value << shift;
 532
 533        s->addr = (s->addr & mask) | v;
 534        s->addrlen ++;
 535
 536        switch (s->addrlen) {
 537        case 1:
 538            if (s->cmd == NAND_CMD_READID) {
 539                nand_command(s);
 540            }
 541            break;
 542        case 2: /* fix cache address as a byte address */
 543            s->addr <<= (s->buswidth - 1);
 544            break;
 545        case 3:
 546            if (!(nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) &&
 547                    (s->cmd == NAND_CMD_READ0 ||
 548                     s->cmd == NAND_CMD_PAGEPROGRAM1)) {
 549                nand_command(s);
 550            }
 551            break;
 552        case 4:
 553            if ((nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) &&
 554                    nand_flash_ids[s->chip_id].size < 256 && /* 1Gb or less */
 555                    (s->cmd == NAND_CMD_READ0 ||
 556                     s->cmd == NAND_CMD_PAGEPROGRAM1)) {
 557                nand_command(s);
 558            }
 559            break;
 560        case 5:
 561            if ((nand_flash_ids[s->chip_id].options & NAND_SAMSUNG_LP) &&
 562                    nand_flash_ids[s->chip_id].size >= 256 && /* 2Gb or more */
 563                    (s->cmd == NAND_CMD_READ0 ||
 564                     s->cmd == NAND_CMD_PAGEPROGRAM1)) {
 565                nand_command(s);
 566            }
 567            break;
 568        default:
 569            break;
 570        }
 571    }
 572
 573    if (!s->cle && !s->ale && s->cmd == NAND_CMD_PAGEPROGRAM1) {
 574        if (s->iolen < (1 << s->page_shift) + (1 << s->oob_shift)) {
 575            for (i = s->buswidth; i--; value >>= 8) {
 576                s->io[s->iolen ++] = (uint8_t) (value & 0xff);
 577            }
 578        }
 579    } else if (!s->cle && !s->ale && s->cmd == NAND_CMD_COPYBACKPRG1) {
 580        if ((s->addr & ((1 << s->addr_shift) - 1)) <
 581                (1 << s->page_shift) + (1 << s->oob_shift)) {
 582            for (i = s->buswidth; i--; s->addr++, value >>= 8) {
 583                s->io[s->iolen + (s->addr & ((1 << s->addr_shift) - 1))] =
 584                    (uint8_t) (value & 0xff);
 585            }
 586        }
 587    }
 588}
 589
 590uint32_t nand_getio(DeviceState *dev)
 591{
 592    int offset;
 593    uint32_t x = 0;
 594    NANDFlashState *s = NAND(dev);
 595
 596    /* Allow sequential reading */
 597    if (!s->iolen && s->cmd == NAND_CMD_READ0) {
 598        offset = (int) (s->addr & ((1 << s->addr_shift) - 1)) + s->offset;
 599        s->offset = 0;
 600
 601        s->blk_load(s, s->addr, offset);
 602        if (s->gnd)
 603            s->iolen = (1 << s->page_shift) - offset;
 604        else
 605            s->iolen = (1 << s->page_shift) + (1 << s->oob_shift) - offset;
 606    }
 607
 608    if (s->ce || s->iolen <= 0) {
 609        return 0;
 610    }
 611
 612    for (offset = s->buswidth; offset--;) {
 613        x |= s->ioaddr[offset] << (offset << 3);
 614    }
 615    /* after receiving READ STATUS command all subsequent reads will
 616     * return the status register value until another command is issued
 617     */
 618    if (s->cmd != NAND_CMD_READSTATUS) {
 619        s->addr   += s->buswidth;
 620        s->ioaddr += s->buswidth;
 621        s->iolen  -= s->buswidth;
 622    }
 623    return x;
 624}
 625
 626uint32_t nand_getbuswidth(DeviceState *dev)
 627{
 628    NANDFlashState *s = (NANDFlashState *) dev;
 629    return s->buswidth << 3;
 630}
 631
 632DeviceState *nand_init(BlockBackend *blk, int manf_id, int chip_id)
 633{
 634    DeviceState *dev;
 635
 636    if (nand_flash_ids[chip_id].size == 0) {
 637        hw_error("%s: Unsupported NAND chip ID.\n", __func__);
 638    }
 639    dev = qdev_new(TYPE_NAND);
 640    qdev_prop_set_uint8(dev, "manufacturer_id", manf_id);
 641    qdev_prop_set_uint8(dev, "chip_id", chip_id);
 642    if (blk) {
 643        qdev_prop_set_drive_err(dev, "drive", blk, &error_fatal);
 644    }
 645
 646    qdev_realize(dev, NULL, &error_fatal);
 647    return dev;
 648}
 649
 650type_init(nand_register_types)
 651
 652#else
 653
 654/* Program a single page */
 655static void glue(nand_blk_write_, NAND_PAGE_SIZE)(NANDFlashState *s)
 656{
 657    uint64_t off, page, sector, soff;
 658    uint8_t iobuf[(PAGE_SECTORS + 2) * 0x200];
 659    if (PAGE(s->addr) >= s->pages)
 660        return;
 661
 662    if (!s->blk) {
 663        mem_and(s->storage + PAGE_START(s->addr) + (s->addr & PAGE_MASK) +
 664                        s->offset, s->io, s->iolen);
 665    } else if (s->mem_oob) {
 666        sector = SECTOR(s->addr);
 667        off = (s->addr & PAGE_MASK) + s->offset;
 668        soff = SECTOR_OFFSET(s->addr);
 669        if (blk_pread(s->blk, sector << BDRV_SECTOR_BITS, iobuf,
 670                      PAGE_SECTORS << BDRV_SECTOR_BITS) < 0) {
 671            printf("%s: read error in sector %" PRIu64 "\n", __func__, sector);
 672            return;
 673        }
 674
 675        mem_and(iobuf + (soff | off), s->io, MIN(s->iolen, NAND_PAGE_SIZE - off));
 676        if (off + s->iolen > NAND_PAGE_SIZE) {
 677            page = PAGE(s->addr);
 678            mem_and(s->storage + (page << OOB_SHIFT), s->io + NAND_PAGE_SIZE - off,
 679                            MIN(OOB_SIZE, off + s->iolen - NAND_PAGE_SIZE));
 680        }
 681
 682        if (blk_pwrite(s->blk, sector << BDRV_SECTOR_BITS, iobuf,
 683                       PAGE_SECTORS << BDRV_SECTOR_BITS, 0) < 0) {
 684            printf("%s: write error in sector %" PRIu64 "\n", __func__, sector);
 685        }
 686    } else {
 687        off = PAGE_START(s->addr) + (s->addr & PAGE_MASK) + s->offset;
 688        sector = off >> 9;
 689        soff = off & 0x1ff;
 690        if (blk_pread(s->blk, sector << BDRV_SECTOR_BITS, iobuf,
 691                      (PAGE_SECTORS + 2) << BDRV_SECTOR_BITS) < 0) {
 692            printf("%s: read error in sector %" PRIu64 "\n", __func__, sector);
 693            return;
 694        }
 695
 696        mem_and(iobuf + soff, s->io, s->iolen);
 697
 698        if (blk_pwrite(s->blk, sector << BDRV_SECTOR_BITS, iobuf,
 699                       (PAGE_SECTORS + 2) << BDRV_SECTOR_BITS, 0) < 0) {
 700            printf("%s: write error in sector %" PRIu64 "\n", __func__, sector);
 701        }
 702    }
 703    s->offset = 0;
 704}
 705
 706/* Erase a single block */
 707static void glue(nand_blk_erase_, NAND_PAGE_SIZE)(NANDFlashState *s)
 708{
 709    uint64_t i, page, addr;
 710    uint8_t iobuf[0x200] = { [0 ... 0x1ff] = 0xff, };
 711    addr = s->addr & ~((1 << (ADDR_SHIFT + s->erase_shift)) - 1);
 712
 713    if (PAGE(addr) >= s->pages) {
 714        return;
 715    }
 716
 717    if (!s->blk) {
 718        memset(s->storage + PAGE_START(addr),
 719                        0xff, (NAND_PAGE_SIZE + OOB_SIZE) << s->erase_shift);
 720    } else if (s->mem_oob) {
 721        memset(s->storage + (PAGE(addr) << OOB_SHIFT),
 722                        0xff, OOB_SIZE << s->erase_shift);
 723        i = SECTOR(addr);
 724        page = SECTOR(addr + (1 << (ADDR_SHIFT + s->erase_shift)));
 725        for (; i < page; i ++)
 726            if (blk_pwrite(s->blk, i << BDRV_SECTOR_BITS, iobuf,
 727                           BDRV_SECTOR_SIZE, 0) < 0) {
 728                printf("%s: write error in sector %" PRIu64 "\n", __func__, i);
 729            }
 730    } else {
 731        addr = PAGE_START(addr);
 732        page = addr >> 9;
 733        if (blk_pread(s->blk, page << BDRV_SECTOR_BITS, iobuf,
 734                      BDRV_SECTOR_SIZE) < 0) {
 735            printf("%s: read error in sector %" PRIu64 "\n", __func__, page);
 736        }
 737        memset(iobuf + (addr & 0x1ff), 0xff, (~addr & 0x1ff) + 1);
 738        if (blk_pwrite(s->blk, page << BDRV_SECTOR_BITS, iobuf,
 739                       BDRV_SECTOR_SIZE, 0) < 0) {
 740            printf("%s: write error in sector %" PRIu64 "\n", __func__, page);
 741        }
 742
 743        memset(iobuf, 0xff, 0x200);
 744        i = (addr & ~0x1ff) + 0x200;
 745        for (addr += ((NAND_PAGE_SIZE + OOB_SIZE) << s->erase_shift) - 0x200;
 746                        i < addr; i += 0x200) {
 747            if (blk_pwrite(s->blk, i, iobuf, BDRV_SECTOR_SIZE, 0) < 0) {
 748                printf("%s: write error in sector %" PRIu64 "\n",
 749                       __func__, i >> 9);
 750            }
 751        }
 752
 753        page = i >> 9;
 754        if (blk_pread(s->blk, page << BDRV_SECTOR_BITS, iobuf,
 755                      BDRV_SECTOR_SIZE) < 0) {
 756            printf("%s: read error in sector %" PRIu64 "\n", __func__, page);
 757        }
 758        memset(iobuf, 0xff, ((addr - 1) & 0x1ff) + 1);
 759        if (blk_pwrite(s->blk, page << BDRV_SECTOR_BITS, iobuf,
 760                       BDRV_SECTOR_SIZE, 0) < 0) {
 761            printf("%s: write error in sector %" PRIu64 "\n", __func__, page);
 762        }
 763    }
 764}
 765
 766static void glue(nand_blk_load_, NAND_PAGE_SIZE)(NANDFlashState *s,
 767                uint64_t addr, int offset)
 768{
 769    if (PAGE(addr) >= s->pages) {
 770        return;
 771    }
 772
 773    if (s->blk) {
 774        if (s->mem_oob) {
 775            if (blk_pread(s->blk, SECTOR(addr) << BDRV_SECTOR_BITS, s->io,
 776                          PAGE_SECTORS << BDRV_SECTOR_BITS) < 0) {
 777                printf("%s: read error in sector %" PRIu64 "\n",
 778                                __func__, SECTOR(addr));
 779            }
 780            memcpy(s->io + SECTOR_OFFSET(s->addr) + NAND_PAGE_SIZE,
 781                            s->storage + (PAGE(s->addr) << OOB_SHIFT),
 782                            OOB_SIZE);
 783            s->ioaddr = s->io + SECTOR_OFFSET(s->addr) + offset;
 784        } else {
 785            if (blk_pread(s->blk, PAGE_START(addr), s->io,
 786                          (PAGE_SECTORS + 2) << BDRV_SECTOR_BITS) < 0) {
 787                printf("%s: read error in sector %" PRIu64 "\n",
 788                                __func__, PAGE_START(addr) >> 9);
 789            }
 790            s->ioaddr = s->io + (PAGE_START(addr) & 0x1ff) + offset;
 791        }
 792    } else {
 793        memcpy(s->io, s->storage + PAGE_START(s->addr) +
 794                        offset, NAND_PAGE_SIZE + OOB_SIZE - offset);
 795        s->ioaddr = s->io;
 796    }
 797}
 798
 799static void glue(nand_init_, NAND_PAGE_SIZE)(NANDFlashState *s)
 800{
 801    s->oob_shift = PAGE_SHIFT - 5;
 802    s->pages = s->size >> PAGE_SHIFT;
 803    s->addr_shift = ADDR_SHIFT;
 804
 805    s->blk_erase = glue(nand_blk_erase_, NAND_PAGE_SIZE);
 806    s->blk_write = glue(nand_blk_write_, NAND_PAGE_SIZE);
 807    s->blk_load = glue(nand_blk_load_, NAND_PAGE_SIZE);
 808}
 809
 810# undef NAND_PAGE_SIZE
 811# undef PAGE_SHIFT
 812# undef PAGE_SECTORS
 813# undef ADDR_SHIFT
 814#endif  /* NAND_IO */
 815