aboutsummaryrefslogtreecommitdiff
path: root/common/aboot.c
diff options
context:
space:
mode:
Diffstat (limited to 'common/aboot.c')
-rw-r--r--common/aboot.c34
1 files changed, 24 insertions, 10 deletions
diff --git a/common/aboot.c b/common/aboot.c
index 1cfc606dd4..54374c9f17 100644
--- a/common/aboot.c
+++ b/common/aboot.c
@@ -41,27 +41,32 @@
#include <part.h>
#include <sparse_format.h>
#include <linux/sizes.h>
+#include <linux/kernel.h>
-#ifndef CONFIG_FILL_BUFF_SIZE
-#define CONFIG_FILL_BUFF_SIZE SZ_4M
+#ifndef CONFIG_FILL_BUFF_MAX_SIZE
+#define CONFIG_FILL_BUFF_MAX_SIZE SZ_4M
#endif
static int write_fill_multi_blks(block_dev_desc_t *dev_desc,
disk_partition_t *info,
lbaint_t *blk, lbaint_t blkcnt, uint32_t fill_val)
{
- int i, size;;
+ int i, size, order;
uint32_t *fill_buf;
lbaint_t blks, fill_cnt, written_blks = 0;
- fill_cnt = CONFIG_FILL_BUFF_SIZE / info->blksz;
- lbaint_t quot = blkcnt / fill_cnt;
- lbaint_t remd = blkcnt % fill_cnt;
-
- size = blkcnt > fill_cnt ? CONFIG_FILL_BUFF_SIZE : (blkcnt * info->blksz);
+ order = get_order(MIN(CONFIG_FILL_BUFF_MAX_SIZE, (blkcnt * info->blksz)),
+ info->blksz);
- fill_buf = (uint32_t *) memalign(ARCH_DMA_MINALIGN,
+ while(order >= 0) {
+ size = info->blksz << order;
+ fill_buf = (uint32_t *) memalign(ARCH_DMA_MINALIGN,
ROUNDUP(size, ARCH_DMA_MINALIGN));
+ if (fill_buf)
+ break;
+
+ order--;
+ }
if (!fill_buf) {
fastboot_fail(
@@ -69,6 +74,13 @@ static int write_fill_multi_blks(block_dev_desc_t *dev_desc,
return -1;
}
+ fill_cnt = 0x1 << order;
+ lbaint_t quot = blkcnt / fill_cnt;
+ lbaint_t remd = blkcnt % fill_cnt;
+
+ if (blkcnt < fill_cnt)
+ size = blkcnt * info->blksz;
+
for (i = 0; i < (size / sizeof(fill_val)); i++)
fill_buf[i] = fill_val;
@@ -237,7 +249,9 @@ void write_sparse_image(block_dev_desc_t *dev_desc,
fill_val = *(uint32_t *)data;
data = (char *) data + sizeof(uint32_t);
- write_fill_multi_blks(dev_desc, info, &blk, blkcnt, fill_val);
+ if (write_fill_multi_blks(dev_desc, info, &blk,
+ blkcnt, fill_val) < 0)
+ return;
bytes_written += blkcnt * info->blksz;
total_blocks += chunk_data_sz / sparse_header->blk_sz;