aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRod Whitby <rod@whitby.id.au>2006-12-05 20:41:15 -0500
committerDavid Woodhouse <dwmw2@infradead.org>2006-12-08 08:28:26 -0500
commitf33665d931f33a0baf44fc5d3594b23f8118eb44 (patch)
tree21c95d1594395c5d9dc69c7483cae186ce9a5b84
parentdd11b8cdf0c455f4cfbc5daa70aabce9dcc6c07b (diff)
[MTD] Support combined RedBoot FIS directory and configuration area
RedBoot supports storing the FIS directory and the RedBoot configuration area in the same block of flash memory. This is not the most common RedBoot configuration, but it is used on commercially available boards supported by the kernel. A recent patch to mtd/redboot.c (http://lkml.org/lkml/2006/3/20/410) which corrected the skipping of deleted table entries has exposed the latent problem of the kernel redboot parser running off the end of the FIS directory and interpreting the RedBoot configuration information as table entries. This patch terminates the table parsing when the first truly empty entry is found (table entry deletion only clears the first byte of the name, so two cleared bytes in a row indicates the end of the table), thereby supporting the combined redboot FIS directory and RedBoot configuration information flash layout scenario. Signed-off-by: Rod Whitby <rod@whitby.id.au> Signed-off-by: David Woodhouse <dwmw2@infradead.org>
-rw-r--r--drivers/mtd/redboot.c23
1 files changed, 20 insertions, 3 deletions
diff --git a/drivers/mtd/redboot.c b/drivers/mtd/redboot.c
index b5259215f6d7..035cd9b0cc08 100644
--- a/drivers/mtd/redboot.c
+++ b/drivers/mtd/redboot.c
@@ -96,7 +96,19 @@ static int parse_redboot_partitions(struct mtd_info *master,
96 */ 96 */
97 if (swab32(buf[i].size) == master->erasesize) { 97 if (swab32(buf[i].size) == master->erasesize) {
98 int j; 98 int j;
99 for (j = 0; j < numslots && buf[j].name[0] != 0xff; ++j) { 99 for (j = 0; j < numslots; ++j) {
100
101 /* A single 0xff denotes a deleted entry.
102 * Two of them in a row is the end of the table.
103 */
104 if (buf[j].name[0] == 0xff) {
105 if (buf[j].name[1] == 0xff) {
106 break;
107 } else {
108 continue;
109 }
110 }
111
100 /* The unsigned long fields were written with the 112 /* The unsigned long fields were written with the
101 * wrong byte sex, name and pad have no byte sex. 113 * wrong byte sex, name and pad have no byte sex.
102 */ 114 */
@@ -126,8 +138,13 @@ static int parse_redboot_partitions(struct mtd_info *master,
126 for (i = 0; i < numslots; i++) { 138 for (i = 0; i < numslots; i++) {
127 struct fis_list *new_fl, **prev; 139 struct fis_list *new_fl, **prev;
128 140
129 if (buf[i].name[0] == 0xff) 141 if (buf[i].name[0] == 0xff) {
130 continue; 142 if (buf[i].name[1] == 0xff) {
143 break;
144 } else {
145 continue;
146 }
147 }
131 if (!redboot_checksum(&buf[i])) 148 if (!redboot_checksum(&buf[i]))
132 break; 149 break;
133 150