aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorbalrog <balrog@c046a42c-6fe2-441c-8c8c-71466251a162>2008-12-07 12:36:28 +0000
committerbalrog <balrog@c046a42c-6fe2-441c-8c8c-71466251a162>2008-12-07 12:36:28 +0000
commitd361be2566e01f59d49f8102a5af2820cbaf8e73 (patch)
tree8636ba4d06056f6789bd014247e2b1eda4aaffa2
parent575750581c6ea70e89a7889cb6028f234f9d2ee9 (diff)
pflash_cfi01: add Single Byte Program (Jean-Christophe PLAGNIOL-VILLARD).
Signed-off-by: Jean-Christophe PLAGNIOL-VILLARD <plagnioj@jcrosoft.com> Signed-off-by: Andrzej Zaborowski <andrew.zaborowski@intel.com> git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5904 c046a42c-6fe2-441c-8c8c-71466251a162
-rw-r--r--hw/pflash_cfi01.c87
1 files changed, 53 insertions, 34 deletions
diff --git a/hw/pflash_cfi01.c b/hw/pflash_cfi01.c
index 6113fa648b..6f97e9d838 100644
--- a/hw/pflash_cfi01.c
+++ b/hw/pflash_cfi01.c
@@ -194,6 +194,47 @@ static void pflash_update(pflash_t *pfl, int offset,
}
}
+static void inline pflash_data_write(pflash_t *pfl, target_ulong offset,
+ uint32_t value, int width)
+{
+ uint8_t *p = pfl->storage;
+
+ DPRINTF("%s: block write offset " TARGET_FMT_lx
+ " value %x counter " TARGET_FMT_lx "\n",
+ __func__, offset, value, pfl->counter);
+ switch (width) {
+ case 1:
+ p[offset] = value;
+ pflash_update(pfl, offset, 1);
+ break;
+ case 2:
+#if defined(TARGET_WORDS_BIGENDIAN)
+ p[offset] = value >> 8;
+ p[offset + 1] = value;
+#else
+ p[offset] = value;
+ p[offset + 1] = value >> 8;
+#endif
+ pflash_update(pfl, offset, 2);
+ break;
+ case 4:
+#if defined(TARGET_WORDS_BIGENDIAN)
+ p[offset] = value >> 24;
+ p[offset + 1] = value >> 16;
+ p[offset + 2] = value >> 8;
+ p[offset + 3] = value;
+#else
+ p[offset] = value;
+ p[offset + 1] = value >> 8;
+ p[offset + 2] = value >> 16;
+ p[offset + 3] = value >> 24;
+#endif
+ pflash_update(pfl, offset, 4);
+ break;
+ }
+
+}
+
static void pflash_write (pflash_t *pfl, target_ulong offset, uint32_t value,
int width)
{
@@ -221,6 +262,10 @@ static void pflash_write (pflash_t *pfl, target_ulong offset, uint32_t value,
switch (cmd) {
case 0x00: /* ??? */
goto reset_flash;
+ case 0x10: /* Single Byte Program */
+ case 0x40: /* Single Byte Program */
+ DPRINTF(stderr, "%s: Single Byte Program\n", __func__);
+ break;
case 0x20: /* Block erase */
p = pfl->storage;
offset &= ~(pfl->sector_len - 1);
@@ -262,6 +307,13 @@ static void pflash_write (pflash_t *pfl, target_ulong offset, uint32_t value,
return;
case 1:
switch (pfl->cmd) {
+ case 0x10: /* Single Byte Program */
+ case 0x40: /* Single Byte Program */
+ DPRINTF("%s: Single Byte Program\n", __func__);
+ pflash_data_write(pfl, offset, value, width);
+ pfl->status |= 0x80; /* Ready! */
+ pfl->wcycle = 0;
+ break;
case 0x20: /* Block erase */
case 0x28:
if (cmd == 0xd0) { /* confirm */
@@ -306,40 +358,7 @@ static void pflash_write (pflash_t *pfl, target_ulong offset, uint32_t value,
case 2:
switch (pfl->cmd) {
case 0xe8: /* Block write */
- p = pfl->storage;
- DPRINTF("%s: block write offset " TARGET_FMT_lx
- " value %x counter " TARGET_FMT_lx "\n",
- __func__, offset, value, pfl->counter);
- switch (width) {
- case 1:
- p[offset] = value;
- pflash_update(pfl, offset, 1);
- break;
- case 2:
-#if defined(TARGET_WORDS_BIGENDIAN)
- p[offset] = value >> 8;
- p[offset + 1] = value;
-#else
- p[offset] = value;
- p[offset + 1] = value >> 8;
-#endif
- pflash_update(pfl, offset, 2);
- break;
- case 4:
-#if defined(TARGET_WORDS_BIGENDIAN)
- p[offset] = value >> 24;
- p[offset + 1] = value >> 16;
- p[offset + 2] = value >> 8;
- p[offset + 3] = value;
-#else
- p[offset] = value;
- p[offset + 1] = value >> 8;
- p[offset + 2] = value >> 16;
- p[offset + 3] = value >> 24;
-#endif
- pflash_update(pfl, offset, 4);
- break;
- }
+ pflash_data_write(pfl, offset, value, width);
pfl->status |= 0x80;