[PATCH 0/3] Patches to allow running u-boot on vocore2 board

There are two distinct things here: - a few small fixes specific to vocore2 board. - fixes to SquashFS to allow compilation on 32-bit architectures.
Mauro Condarelli (3): Small fixes to reduce size and ensure correct console output. Enlarge SPL malloc area to prevent failure in lzma decompression. Fix missing __udivdi3 in SquashFS implementation.
arch/mips/dts/vocore_vocore2.dts | 2 +- configs/vocore2_defconfig | 2 +- fs/squashfs/sqfs.c | 45 ++++++++++++++++++++------------ fs/squashfs/sqfs_inode.c | 8 +++--- include/configs/vocore2.h | 4 ++- 5 files changed, 38 insertions(+), 23 deletions(-)

Signed-off-by: Mauro Condarelli mc5686@mclink.it --- arch/mips/dts/vocore_vocore2.dts | 2 +- include/configs/vocore2.h | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/arch/mips/dts/vocore_vocore2.dts b/arch/mips/dts/vocore_vocore2.dts index 3502e4b8b7..9adf39652f 100644 --- a/arch/mips/dts/vocore_vocore2.dts +++ b/arch/mips/dts/vocore_vocore2.dts @@ -59,7 +59,7 @@ #address-cells = <1>; #size-cells = <1>; compatible = "jedec,spi-nor"; - spi-max-frequency = <25000000>; + spi-max-frequency = <40000000>; reg = <0>; }; }; diff --git a/include/configs/vocore2.h b/include/configs/vocore2.h index 40467b737c..29a57ad233 100644 --- a/include/configs/vocore2.h +++ b/include/configs/vocore2.h @@ -25,6 +25,7 @@ #define CONFIG_SPL_BSS_START_ADDR 0x80010000 #define CONFIG_SPL_BSS_MAX_SIZE 0x10000 #define CONFIG_SPL_MAX_SIZE 0x10000 +#define CONFIG_SPL_PAD_TO 0
/* Dummy value */ #define CONFIG_SYS_UBOOT_BASE 0 @@ -34,6 +35,7 @@ #define CONFIG_SYS_NS16550_CLK 40000000 #define CONFIG_SYS_NS16550_REG_SIZE -4 #define CONFIG_SYS_NS16550_COM3 0xb0000e00 +#define CONFIG_CONS_INDEX 3
/* RAM */

Signed-off-by: Mauro Condarelli mc5686@mclink.it --- configs/vocore2_defconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/configs/vocore2_defconfig b/configs/vocore2_defconfig index 99a1143e6e..5776aada15 100644 --- a/configs/vocore2_defconfig +++ b/configs/vocore2_defconfig @@ -6,7 +6,7 @@ CONFIG_ENV_SIZE=0x1000 CONFIG_ENV_OFFSET=0x04e000 CONFIG_ENV_SECT_SIZE=0x1000 CONFIG_SYS_BOOTCOUNT_ADDR=0xb000006c -CONFIG_SPL_SYS_MALLOC_F_LEN=0x20000 +CONFIG_SPL_SYS_MALLOC_F_LEN=0x40000 CONFIG_SPL=y CONFIG_SYS_BOOTCOUNT_SINGLEWORD=y CONFIG_ARCH_MTMIPS=y

Signed-off-by: Mauro Condarelli mc5686@mclink.it --- fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +- 3 files changed, 34 insertions(+), 21 deletions(-)
diff --git a/fs/squashfs/sqfs.c b/fs/squashfs/sqfs.c index 15208b4dab..b49331ce93 100644 --- a/fs/squashfs/sqfs.c +++ b/fs/squashfs/sqfs.c @@ -18,6 +18,8 @@ #include <string.h> #include <squashfs.h> #include <part.h> +#include <div64.h> +#include <stdio.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -82,13 +84,16 @@ static int sqfs_count_tokens(const char *filename) */ static int sqfs_calc_n_blks(__le64 start, __le64 end, u64 *offset) { - u64 start_, table_size; + u64 start_, table_size, blks;
table_size = le64_to_cpu(end) - le64_to_cpu(start); - start_ = le64_to_cpu(start) / ctxt.cur_dev->blksz; + start_ = le64_to_cpu(start); + do_div(start_, ctxt.cur_dev->blksz); *offset = le64_to_cpu(start) - (start_ * ctxt.cur_dev->blksz);
- return DIV_ROUND_UP(table_size + *offset, ctxt.cur_dev->blksz); + blks = table_size + *offset; + if (do_div(blks, ctxt.cur_dev->blksz)) blks++; + return blks; }
/* @@ -109,8 +114,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, if (inode_fragment_index >= get_unaligned_le32(&sblk->fragments)) return -EINVAL;
- start = get_unaligned_le64(&sblk->fragment_table_start) / - ctxt.cur_dev->blksz; + start = get_unaligned_le64(&sblk->fragment_table_start); + do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->fragment_table_start, sblk->export_table_start, &table_offset); @@ -135,7 +140,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, start_block = get_unaligned_le64(table + table_offset + block * sizeof(u64));
- start = start_block / ctxt.cur_dev->blksz; + start = start_block; + do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(cpu_to_le64(start_block), sblk->fragment_table_start, &table_offset);
@@ -641,8 +647,8 @@ static int sqfs_read_inode_table(unsigned char **inode_table)
table_size = get_unaligned_le64(&sblk->directory_table_start) - get_unaligned_le64(&sblk->inode_table_start); - start = get_unaligned_le64(&sblk->inode_table_start) / - ctxt.cur_dev->blksz; + start = get_unaligned_le64(&sblk->inode_table_start); + do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->inode_table_start, sblk->directory_table_start, &table_offset);
@@ -725,8 +731,8 @@ static int sqfs_read_directory_table(unsigned char **dir_table, u32 **pos_list) /* DIRECTORY TABLE */ table_size = get_unaligned_le64(&sblk->fragment_table_start) - get_unaligned_le64(&sblk->directory_table_start); - start = get_unaligned_le64(&sblk->directory_table_start) / - ctxt.cur_dev->blksz; + start = get_unaligned_le64(&sblk->directory_table_start); + do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->directory_table_start, sblk->fragment_table_start, &table_offset);
@@ -1158,6 +1164,7 @@ static int sqfs_get_regfile_info(struct squashfs_reg_inode *reg, fentry); if (ret < 0) return -EINVAL; + finfo->comp = true; if (fentry->size < 1 || fentry->start == 0x7FFFFFFF) return -EINVAL; @@ -1328,17 +1335,19 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, data_offset = finfo.start; datablock = malloc(get_unaligned_le32(&sblk->block_size)); if (!datablock) { + printf("Error: malloc(%u) failed.\n", get_unaligned_le32(&sblk->block_size)); ret = -ENOMEM; goto free_paths; } }
for (j = 0; j < datablk_count; j++) { - start = data_offset / ctxt.cur_dev->blksz; + start = data_offset; + do_div(start, ctxt.cur_dev->blksz); table_size = SQFS_BLOCK_SIZE(finfo.blk_sizes[j]); table_offset = data_offset - (start * ctxt.cur_dev->blksz); - n_blks = DIV_ROUND_UP(table_size + table_offset, - ctxt.cur_dev->blksz); + n_blks = table_size + table_offset; + if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
data_buffer = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
@@ -1365,8 +1374,10 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, dest_len = get_unaligned_le32(&sblk->block_size); ret = sqfs_decompress(&ctxt, datablock, &dest_len, data, table_size); - if (ret) + if (ret) { + printf("Errrt: block decompress failed.\n"); goto free_buffer; + }
memcpy(buf + offset + *actread, datablock, dest_len); *actread += dest_len; @@ -1388,10 +1399,12 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, goto free_buffer; }
- start = frag_entry.start / ctxt.cur_dev->blksz; + start = frag_entry.start; + do_div(start, ctxt.cur_dev->blksz); table_size = SQFS_BLOCK_SIZE(frag_entry.size); table_offset = frag_entry.start - (start * ctxt.cur_dev->blksz); - n_blks = DIV_ROUND_UP(table_size + table_offset, ctxt.cur_dev->blksz); + n_blks = table_size + table_offset; + if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
fragment = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
diff --git a/fs/squashfs/sqfs_inode.c b/fs/squashfs/sqfs_inode.c index 1368f3063c..c330e32a0e 100644 --- a/fs/squashfs/sqfs_inode.c +++ b/fs/squashfs/sqfs_inode.c @@ -11,6 +11,7 @@ #include <stdio.h> #include <stdlib.h> #include <string.h> +#include <div64.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -67,10 +68,9 @@ int sqfs_inode_size(struct squashfs_base_inode *inode, u32 blk_size) u64 file_size = get_unaligned_le64(&lreg->file_size); unsigned int blk_list_size;
- if (fragment == 0xFFFFFFFF) - blk_list_size = DIV_ROUND_UP(file_size, blk_size); - else - blk_list_size = file_size / blk_size; + if (do_div(file_size, blk_size) && (fragment == 0xFFFFFFFF)) + file_size++; + blk_list_size = file_size;
return sizeof(*lreg) + blk_list_size * sizeof(u32); } diff --git a/include/configs/vocore2.h b/include/configs/vocore2.h index 29a57ad233..dfdb8fcc04 100644 --- a/include/configs/vocore2.h +++ b/include/configs/vocore2.h @@ -41,7 +41,7 @@
/* Memory usage */ #define CONFIG_SYS_MAXARGS 64 -#define CONFIG_SYS_MALLOC_LEN (1024 * 1024) +#define CONFIG_SYS_MALLOC_LEN (16 * 1024 * 1024) #define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) #define CONFIG_SYS_CBSIZE 512

On Sun, Sep 20, 2020 at 06:29:01PM +0200, Mauro Condarelli wrote:
Signed-off-by: Mauro Condarelli mc5686@mclink.it
fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +- 3 files changed, 34 insertions(+), 21 deletions(-)
diff --git a/fs/squashfs/sqfs.c b/fs/squashfs/sqfs.c index 15208b4dab..b49331ce93 100644 --- a/fs/squashfs/sqfs.c +++ b/fs/squashfs/sqfs.c @@ -18,6 +18,8 @@ #include <string.h> #include <squashfs.h> #include <part.h> +#include <div64.h> +#include <stdio.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -82,13 +84,16 @@ static int sqfs_count_tokens(const char *filename) */ static int sqfs_calc_n_blks(__le64 start, __le64 end, u64 *offset) {
- u64 start_, table_size;
u64 start_, table_size, blks;
table_size = le64_to_cpu(end) - le64_to_cpu(start);
- start_ = le64_to_cpu(start) / ctxt.cur_dev->blksz;
- start_ = le64_to_cpu(start);
- do_div(start_, ctxt.cur_dev->blksz); *offset = le64_to_cpu(start) - (start_ * ctxt.cur_dev->blksz);
- return DIV_ROUND_UP(table_size + *offset, ctxt.cur_dev->blksz);
- blks = table_size + *offset;
- if (do_div(blks, ctxt.cur_dev->blksz)) blks++;
- return blks;
}
/* @@ -109,8 +114,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, if (inode_fragment_index >= get_unaligned_le32(&sblk->fragments)) return -EINVAL;
- start = get_unaligned_le64(&sblk->fragment_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->fragment_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->fragment_table_start, sblk->export_table_start, &table_offset);
@@ -135,7 +140,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, start_block = get_unaligned_le64(table + table_offset + block * sizeof(u64));
- start = start_block / ctxt.cur_dev->blksz;
- start = start_block;
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(cpu_to_le64(start_block), sblk->fragment_table_start, &table_offset);
@@ -641,8 +647,8 @@ static int sqfs_read_inode_table(unsigned char **inode_table)
table_size = get_unaligned_le64(&sblk->directory_table_start) - get_unaligned_le64(&sblk->inode_table_start);
- start = get_unaligned_le64(&sblk->inode_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->inode_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->inode_table_start, sblk->directory_table_start, &table_offset);
@@ -725,8 +731,8 @@ static int sqfs_read_directory_table(unsigned char **dir_table, u32 **pos_list) /* DIRECTORY TABLE */ table_size = get_unaligned_le64(&sblk->fragment_table_start) - get_unaligned_le64(&sblk->directory_table_start);
- start = get_unaligned_le64(&sblk->directory_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->directory_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->directory_table_start, sblk->fragment_table_start, &table_offset);
@@ -1158,6 +1164,7 @@ static int sqfs_get_regfile_info(struct squashfs_reg_inode *reg, fentry); if (ret < 0) return -EINVAL;
- finfo->comp = true; if (fentry->size < 1 || fentry->start == 0x7FFFFFFF) return -EINVAL;
@@ -1328,17 +1335,19 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, data_offset = finfo.start; datablock = malloc(get_unaligned_le32(&sblk->block_size)); if (!datablock) {
printf("Error: malloc(%u) failed.\n", get_unaligned_le32(&sblk->block_size)); ret = -ENOMEM; goto free_paths;
} }
for (j = 0; j < datablk_count; j++) {
start = data_offset / ctxt.cur_dev->blksz;
start = data_offset;
table_size = SQFS_BLOCK_SIZE(finfo.blk_sizes[j]); table_offset = data_offset - (start * ctxt.cur_dev->blksz);do_div(start, ctxt.cur_dev->blksz);
n_blks = DIV_ROUND_UP(table_size + table_offset,
ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
data_buffer = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
@@ -1365,8 +1374,10 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, dest_len = get_unaligned_le32(&sblk->block_size); ret = sqfs_decompress(&ctxt, datablock, &dest_len, data, table_size);
if (ret)
if (ret) {
printf("Errrt: block decompress failed.\n"); goto free_buffer;
} memcpy(buf + offset + *actread, datablock, dest_len); *actread += dest_len;
@@ -1388,10 +1399,12 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, goto free_buffer; }
- start = frag_entry.start / ctxt.cur_dev->blksz;
- start = frag_entry.start;
- do_div(start, ctxt.cur_dev->blksz); table_size = SQFS_BLOCK_SIZE(frag_entry.size); table_offset = frag_entry.start - (start * ctxt.cur_dev->blksz);
- n_blks = DIV_ROUND_UP(table_size + table_offset, ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
fragment = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
diff --git a/fs/squashfs/sqfs_inode.c b/fs/squashfs/sqfs_inode.c index 1368f3063c..c330e32a0e 100644 --- a/fs/squashfs/sqfs_inode.c +++ b/fs/squashfs/sqfs_inode.c @@ -11,6 +11,7 @@ #include <stdio.h> #include <stdlib.h> #include <string.h> +#include <div64.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -67,10 +68,9 @@ int sqfs_inode_size(struct squashfs_base_inode *inode, u32 blk_size) u64 file_size = get_unaligned_le64(&lreg->file_size); unsigned int blk_list_size;
if (fragment == 0xFFFFFFFF)
blk_list_size = DIV_ROUND_UP(file_size, blk_size);
else
blk_list_size = file_size / blk_size;
if (do_div(file_size, blk_size) && (fragment == 0xFFFFFFFF))
file_size++;
blk_list_size = file_size;
return sizeof(*lreg) + blk_list_size * sizeof(u32); }
diff --git a/include/configs/vocore2.h b/include/configs/vocore2.h index 29a57ad233..dfdb8fcc04 100644 --- a/include/configs/vocore2.h +++ b/include/configs/vocore2.h @@ -41,7 +41,7 @@
/* Memory usage */ #define CONFIG_SYS_MAXARGS 64 -#define CONFIG_SYS_MALLOC_LEN (1024 * 1024) +#define CONFIG_SYS_MALLOC_LEN (16 * 1024 * 1024) #define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) #define CONFIG_SYS_CBSIZE 512
Add in maintainers..

Am Sonntag, den 20.09.2020, 21:21 -0400 schrieb Tom Rini:
On Sun, Sep 20, 2020 at 06:29:01PM +0200, Mauro Condarelli wrote:
Signed-off-by: Mauro Condarelli mc5686@mclink.it
fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +-
remove that file which is unrelated to this patch
3 files changed, 34 insertions(+), 21 deletions(-)
diff --git a/fs/squashfs/sqfs.c b/fs/squashfs/sqfs.c index 15208b4dab..b49331ce93 100644 --- a/fs/squashfs/sqfs.c +++ b/fs/squashfs/sqfs.c @@ -18,6 +18,8 @@ #include <string.h> #include <squashfs.h> #include <part.h> +#include <div64.h> +#include <stdio.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -82,13 +84,16 @@ static int sqfs_count_tokens(const char *filename) */ static int sqfs_calc_n_blks(__le64 start, __le64 end, u64 *offset) {
- u64 start_, table_size;
u64 start_, table_size, blks;
table_size = le64_to_cpu(end) - le64_to_cpu(start);
- start_ = le64_to_cpu(start) / ctxt.cur_dev->blksz;
- start_ = le64_to_cpu(start);
- do_div(start_, ctxt.cur_dev->blksz);
have you tried with lldiv() which returns the 64bit result? Also it would be a little cleaner:
start_ = lldiv(le64_to_cpu(start), ctxt.cur_dev->blksz);
*offset = le64_to_cpu(start) - (start_ * ctxt.cur_dev->blksz);
- return DIV_ROUND_UP(table_size + *offset, ctxt.cur_dev->blksz);
- blks = table_size + *offset;
- if (do_div(blks, ctxt.cur_dev->blksz)) blks++;
- return blks;
maybe define something like this and use that instead of DIV_ROUND_UP:
#define lldiv_round_up(n, d) lldiv((n) + (d) - 1, (d))
}
/* @@ -109,8 +114,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, if (inode_fragment_index >= get_unaligned_le32(&sblk->fragments)) return -EINVAL;
- start = get_unaligned_le64(&sblk->fragment_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->fragment_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->fragment_table_start, sblk->export_table_start, &table_offset);
@@ -135,7 +140,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, start_block = get_unaligned_le64(table + table_offset + block * sizeof(u64));
- start = start_block / ctxt.cur_dev->blksz;
- start = start_block;
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(cpu_to_le64(start_block), sblk->fragment_table_start, &table_offset);
@@ -641,8 +647,8 @@ static int sqfs_read_inode_table(unsigned char **inode_table)
table_size = get_unaligned_le64(&sblk->directory_table_start) - get_unaligned_le64(&sblk->inode_table_start);
- start = get_unaligned_le64(&sblk->inode_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->inode_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->inode_table_start, sblk->directory_table_start, &table_offset);
@@ -725,8 +731,8 @@ static int sqfs_read_directory_table(unsigned char **dir_table, u32 **pos_list) /* DIRECTORY TABLE */ table_size = get_unaligned_le64(&sblk->fragment_table_start) - get_unaligned_le64(&sblk->directory_table_start);
- start = get_unaligned_le64(&sblk->directory_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->directory_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->directory_table_start, sblk->fragment_table_start, &table_offset);
@@ -1158,6 +1164,7 @@ static int sqfs_get_regfile_info(struct squashfs_reg_inode *reg, fentry); if (ret < 0) return -EINVAL;
- finfo->comp = true; if (fentry->size < 1 || fentry->start == 0x7FFFFFFF) return -EINVAL;
@@ -1328,17 +1335,19 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, data_offset = finfo.start; datablock = malloc(get_unaligned_le32(&sblk->block_size)); if (!datablock) {
printf("Error: malloc(%u) failed.\n", get_unaligned_le32(&sblk->block_size)); ret = -ENOMEM; goto free_paths;
} }
for (j = 0; j < datablk_count; j++) {
start = data_offset / ctxt.cur_dev->blksz;
start = data_offset;
table_size = SQFS_BLOCK_SIZE(finfo.blk_sizes[j]); table_offset = data_offset - (start * ctxt.cur_dev->blksz);do_div(start, ctxt.cur_dev->blksz);
n_blks = DIV_ROUND_UP(table_size + table_offset,
ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
data_buffer = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
@@ -1365,8 +1374,10 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, dest_len = get_unaligned_le32(&sblk->block_size); ret = sqfs_decompress(&ctxt, datablock, &dest_len, data, table_size);
if (ret)
if (ret) {
printf("Errrt: block decompress failed.\n"); goto free_buffer;
} memcpy(buf + offset + *actread, datablock, dest_len); *actread += dest_len;
@@ -1388,10 +1399,12 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, goto free_buffer; }
- start = frag_entry.start / ctxt.cur_dev->blksz;
- start = frag_entry.start;
- do_div(start, ctxt.cur_dev->blksz); table_size = SQFS_BLOCK_SIZE(frag_entry.size); table_offset = frag_entry.start - (start * ctxt.cur_dev->blksz);
- n_blks = DIV_ROUND_UP(table_size + table_offset, ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
fragment = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
diff --git a/fs/squashfs/sqfs_inode.c b/fs/squashfs/sqfs_inode.c index 1368f3063c..c330e32a0e 100644 --- a/fs/squashfs/sqfs_inode.c +++ b/fs/squashfs/sqfs_inode.c @@ -11,6 +11,7 @@ #include <stdio.h> #include <stdlib.h> #include <string.h> +#include <div64.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -67,10 +68,9 @@ int sqfs_inode_size(struct squashfs_base_inode *inode, u32 blk_size) u64 file_size = get_unaligned_le64(&lreg->file_size); unsigned int blk_list_size;
if (fragment == 0xFFFFFFFF)
blk_list_size = DIV_ROUND_UP(file_size, blk_size);
else
blk_list_size = file_size / blk_size;
if (do_div(file_size, blk_size) && (fragment == 0xFFFFFFFF))
file_size++;
blk_list_size = file_size;
return sizeof(*lreg) + blk_list_size * sizeof(u32); }
diff --git a/include/configs/vocore2.h b/include/configs/vocore2.h index 29a57ad233..dfdb8fcc04 100644 --- a/include/configs/vocore2.h +++ b/include/configs/vocore2.h @@ -41,7 +41,7 @@
/* Memory usage */ #define CONFIG_SYS_MAXARGS 64 -#define CONFIG_SYS_MALLOC_LEN (1024 * 1024) +#define CONFIG_SYS_MALLOC_LEN (16 * 1024 * 1024) #define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) #define CONFIG_SYS_CBSIZE 512
Add in maintainers..

Thanks for the review, I'll prepare a v2 ASAP.
On 9/23/20 12:05 AM, Daniel Schwierzeck wrote:
Am Sonntag, den 20.09.2020, 21:21 -0400 schrieb Tom Rini:
On Sun, Sep 20, 2020 at 06:29:01PM +0200, Mauro Condarelli wrote:
Signed-off-by: Mauro Condarelli mc5686@mclink.it
fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +-
remove that file which is unrelated to this patch
I will as this is fixing things just for my target and that is clearly wrong. OTOH I feel some provision should be implemented (probably at Config.in level) to ensure SquashFS has enough malloc space for its needs. What are the best practices to handle this?
3 files changed, 34 insertions(+), 21 deletions(-)
diff --git a/fs/squashfs/sqfs.c b/fs/squashfs/sqfs.c index 15208b4dab..b49331ce93 100644 --- a/fs/squashfs/sqfs.c +++ b/fs/squashfs/sqfs.c @@ -18,6 +18,8 @@ #include <string.h> #include <squashfs.h> #include <part.h> +#include <div64.h> +#include <stdio.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -82,13 +84,16 @@ static int sqfs_count_tokens(const char *filename) */ static int sqfs_calc_n_blks(__le64 start, __le64 end, u64 *offset) {
- u64 start_, table_size;
u64 start_, table_size, blks;
table_size = le64_to_cpu(end) - le64_to_cpu(start);
- start_ = le64_to_cpu(start) / ctxt.cur_dev->blksz;
- start_ = le64_to_cpu(start);
- do_div(start_, ctxt.cur_dev->blksz);
have you tried with lldiv() which returns the 64bit result? Also it would be a little cleaner:
start_ = lldiv(le64_to_cpu(start), ctxt.cur_dev->blksz);
I thought of that (actually my first attempt was quite similar, but I noticed that lldiv() actually uses do_div() internally and so I decided to go directly for the lower level (and presumably faster) solution. If You (or the maintainers) feel otherwise I can revert with no problems.
*offset = le64_to_cpu(start) - (start_ * ctxt.cur_dev->blksz);
- return DIV_ROUND_UP(table_size + *offset, ctxt.cur_dev->blksz);
- blks = table_size + *offset;
- if (do_div(blks, ctxt.cur_dev->blksz)) blks++;
- return blks;
maybe define something like this and use that instead of DIV_ROUND_UP:
#define lldiv_round_up(n, d) lldiv((n) + (d) - 1, (d))
Again: IMHO having a macro does not add much value here and using lldiv() only adds a further level of call nesting, but I'm open to switch; I would like to understand the rationale behind these requests, though.
}
/* @@ -109,8 +114,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, if (inode_fragment_index >= get_unaligned_le32(&sblk->fragments)) return -EINVAL;
- start = get_unaligned_le64(&sblk->fragment_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->fragment_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->fragment_table_start, sblk->export_table_start, &table_offset);
@@ -135,7 +140,8 @@ static int sqfs_frag_lookup(u32 inode_fragment_index, start_block = get_unaligned_le64(table + table_offset + block * sizeof(u64));
- start = start_block / ctxt.cur_dev->blksz;
- start = start_block;
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(cpu_to_le64(start_block), sblk->fragment_table_start, &table_offset);
@@ -641,8 +647,8 @@ static int sqfs_read_inode_table(unsigned char **inode_table)
table_size = get_unaligned_le64(&sblk->directory_table_start) - get_unaligned_le64(&sblk->inode_table_start);
- start = get_unaligned_le64(&sblk->inode_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->inode_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->inode_table_start, sblk->directory_table_start, &table_offset);
@@ -725,8 +731,8 @@ static int sqfs_read_directory_table(unsigned char **dir_table, u32 **pos_list) /* DIRECTORY TABLE */ table_size = get_unaligned_le64(&sblk->fragment_table_start) - get_unaligned_le64(&sblk->directory_table_start);
- start = get_unaligned_le64(&sblk->directory_table_start) /
ctxt.cur_dev->blksz;
- start = get_unaligned_le64(&sblk->directory_table_start);
- do_div(start, ctxt.cur_dev->blksz); n_blks = sqfs_calc_n_blks(sblk->directory_table_start, sblk->fragment_table_start, &table_offset);
@@ -1158,6 +1164,7 @@ static int sqfs_get_regfile_info(struct squashfs_reg_inode *reg, fentry); if (ret < 0) return -EINVAL;
- finfo->comp = true; if (fentry->size < 1 || fentry->start == 0x7FFFFFFF) return -EINVAL;
@@ -1328,17 +1335,19 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, data_offset = finfo.start; datablock = malloc(get_unaligned_le32(&sblk->block_size)); if (!datablock) {
printf("Error: malloc(%u) failed.\n", get_unaligned_le32(&sblk->block_size)); ret = -ENOMEM; goto free_paths;
} }
for (j = 0; j < datablk_count; j++) {
start = data_offset / ctxt.cur_dev->blksz;
start = data_offset;
table_size = SQFS_BLOCK_SIZE(finfo.blk_sizes[j]); table_offset = data_offset - (start * ctxt.cur_dev->blksz);do_div(start, ctxt.cur_dev->blksz);
n_blks = DIV_ROUND_UP(table_size + table_offset,
ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
data_buffer = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
@@ -1365,8 +1374,10 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, dest_len = get_unaligned_le32(&sblk->block_size); ret = sqfs_decompress(&ctxt, datablock, &dest_len, data, table_size);
if (ret)
if (ret) {
printf("Errrt: block decompress failed.\n"); goto free_buffer;
} memcpy(buf + offset + *actread, datablock, dest_len); *actread += dest_len;
@@ -1388,10 +1399,12 @@ int sqfs_read(const char *filename, void *buf, loff_t offset, loff_t len, goto free_buffer; }
- start = frag_entry.start / ctxt.cur_dev->blksz;
- start = frag_entry.start;
- do_div(start, ctxt.cur_dev->blksz); table_size = SQFS_BLOCK_SIZE(frag_entry.size); table_offset = frag_entry.start - (start * ctxt.cur_dev->blksz);
- n_blks = DIV_ROUND_UP(table_size + table_offset, ctxt.cur_dev->blksz);
n_blks = table_size + table_offset;
if (do_div(n_blks, ctxt.cur_dev->blksz)) n_blks++;
fragment = malloc_cache_aligned(n_blks * ctxt.cur_dev->blksz);
diff --git a/fs/squashfs/sqfs_inode.c b/fs/squashfs/sqfs_inode.c index 1368f3063c..c330e32a0e 100644 --- a/fs/squashfs/sqfs_inode.c +++ b/fs/squashfs/sqfs_inode.c @@ -11,6 +11,7 @@ #include <stdio.h> #include <stdlib.h> #include <string.h> +#include <div64.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -67,10 +68,9 @@ int sqfs_inode_size(struct squashfs_base_inode *inode, u32 blk_size) u64 file_size = get_unaligned_le64(&lreg->file_size); unsigned int blk_list_size;
if (fragment == 0xFFFFFFFF)
blk_list_size = DIV_ROUND_UP(file_size, blk_size);
else
blk_list_size = file_size / blk_size;
if (do_div(file_size, blk_size) && (fragment == 0xFFFFFFFF))
file_size++;
blk_list_size = file_size;
return sizeof(*lreg) + blk_list_size * sizeof(u32); }
diff --git a/include/configs/vocore2.h b/include/configs/vocore2.h index 29a57ad233..dfdb8fcc04 100644 --- a/include/configs/vocore2.h +++ b/include/configs/vocore2.h @@ -41,7 +41,7 @@
/* Memory usage */ #define CONFIG_SYS_MAXARGS 64 -#define CONFIG_SYS_MALLOC_LEN (1024 * 1024) +#define CONFIG_SYS_MALLOC_LEN (16 * 1024 * 1024) #define CONFIG_SYS_BOOTPARAMS_LEN (128 * 1024) #define CONFIG_SYS_CBSIZE 512
Add in maintainers..
done ;)
I just rebased on later master (some patches did not apply cleanly). I will check again before submitting v2.
Regards Mauro

On Wed, Sep 23, 2020 at 08:27:24PM +0200, Mauro Condarelli wrote:
Thanks for the review, I'll prepare a v2 ASAP.
On 9/23/20 12:05 AM, Daniel Schwierzeck wrote:
Am Sonntag, den 20.09.2020, 21:21 -0400 schrieb Tom Rini:
On Sun, Sep 20, 2020 at 06:29:01PM +0200, Mauro Condarelli wrote:
Signed-off-by: Mauro Condarelli mc5686@mclink.it
fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +-
remove that file which is unrelated to this patch
I will as this is fixing things just for my target and that is clearly wrong. OTOH I feel some provision should be implemented (probably at Config.in level) to ensure SquashFS has enough malloc space for its needs. What are the best practices to handle this?
I don't recall why CONFIG_SYS_MALLOC_LEN hasn't been fully moved to Kconfig right now, there may be a good reason, or it just may be hard. I don't think Kconfig logic supports something like "depends on FOO > 0x4000" so the only way is to note in the squashfs help how much space may be used for malloc in worst cases.

Am Mittwoch, den 23.09.2020, 20:27 +0200 schrieb Mauro Condarelli:
Thanks for the review, I'll prepare a v2 ASAP.
On 9/23/20 12:05 AM, Daniel Schwierzeck wrote:
Am Sonntag, den 20.09.2020, 21:21 -0400 schrieb Tom Rini:
On Sun, Sep 20, 2020 at 06:29:01PM +0200, Mauro Condarelli wrote:
Signed-off-by: Mauro Condarelli mc5686@mclink.it
fs/squashfs/sqfs.c | 45 +++++++++++++++++++++++++-------------- fs/squashfs/sqfs_inode.c | 8 +++---- include/configs/vocore2.h | 2 +-
remove that file which is unrelated to this patch
I will as this is fixing things just for my target and that is clearly wrong. OTOH I feel some provision should be implemented (probably at Config.in level) to ensure SquashFS has enough malloc space for its needs. What are the best practices to handle this?
3 files changed, 34 insertions(+), 21 deletions(-)
diff --git a/fs/squashfs/sqfs.c b/fs/squashfs/sqfs.c index 15208b4dab..b49331ce93 100644 --- a/fs/squashfs/sqfs.c +++ b/fs/squashfs/sqfs.c @@ -18,6 +18,8 @@ #include <string.h> #include <squashfs.h> #include <part.h> +#include <div64.h> +#include <stdio.h>
#include "sqfs_decompressor.h" #include "sqfs_filesystem.h" @@ -82,13 +84,16 @@ static int sqfs_count_tokens(const char *filename) */ static int sqfs_calc_n_blks(__le64 start, __le64 end, u64 *offset) {
- u64 start_, table_size;
u64 start_, table_size, blks;
table_size = le64_to_cpu(end) - le64_to_cpu(start);
- start_ = le64_to_cpu(start) / ctxt.cur_dev->blksz;
- start_ = le64_to_cpu(start);
- do_div(start_, ctxt.cur_dev->blksz);
have you tried with lldiv() which returns the 64bit result? Also it would be a little cleaner:
start_ = lldiv(le64_to_cpu(start), ctxt.cur_dev->blksz);
I thought of that (actually my first attempt was quite similar, but I noticed that lldiv() actually uses do_div() internally and so I decided to go directly for the lower level (and presumably faster) solution. If You (or the maintainers) feel otherwise I can revert with no problems.
because do_div() replaces the dividend with the division remainder and lldiv() returns the division result without modifying the dividend.
Anyway I had a look at the Linux code and other U-Boot file systems and there is a better solution. "struct blk_desc" has a member "int log2blksz" which is initialized as "desc->log2blksz = LOG2(desc-
blksz) in blk-uclass.c. With that you can replace all divisions with
"desc->blksz" as divisor with a simple right bit shift like so:
start_ = le64_to_cpu(start) >> ctxt.cur_dev->log2blksz;
Likewise all multiplications can be replaced with a left bit shift, e.g.:
*offset = le64_to_cpu(start) - (start_ << ctxt.cur_dev->log2blksz);
Also the Linux code never uses DIV_ROUND_UP() for any block related calculations. So maybe all DIV_ROUND_UP() calls can be replaced with a bit shift too.

Am Sonntag, den 20.09.2020, 18:28 +0200 schrieb Mauro Condarelli:
There are two distinct things here:
- a few small fixes specific to vocore2 board.
- fixes to SquashFS to allow compilation on 32-bit architectures.
Mauro Condarelli (3): Small fixes to reduce size and ensure correct console output. Enlarge SPL malloc area to prevent failure in lzma decompression. Fix missing __udivdi3 in SquashFS implementation.
arch/mips/dts/vocore_vocore2.dts | 2 +- configs/vocore2_defconfig | 2 +- fs/squashfs/sqfs.c | 45 ++++++++++++++++++++------------ fs/squashfs/sqfs_inode.c | 8 +++--- include/configs/vocore2.h | 4 ++- 5 files changed, 38 insertions(+), 23 deletions(-)
all vocore2 patches applied to u-boot-mips/fixes, thanks.
Next time please prefix the commit subjects with the subsystem you're changing e.g. "mips: vocore2: XXX" or "squashfs: XXX". I've taken all vocore2 changes and squashed them into one commit to save another patch submission round and to squeeze the fixes into v2020.10.
participants (3)
-
Daniel Schwierzeck
-
Mauro Condarelli
-
Tom Rini