Commit 756c3e67 authored by Chengchang Tang's avatar Chengchang Tang
Browse files

RDMA/hns: Fix integer overflow in calc_loading_percent()

driver inclusion
category: bugfix
bugzilla: https://gitee.com/openeuler/kernel/issues/IAL7SX



----------------------------------------------------------------------

For calc_loading_percent(), if the values of two types of u32 are
multiplied, the result can be an integer overflow. To fix it,
convert all variable to u64.

Since total and free are both size_t, alloc_pages and free_pages
may overflow. In addition, because there is multiplication in the
calculation of percent, it may also cause overflow of u32. In this
patch all relevant variables are converted to u64.

This patch also adds corresponding processing for the exception
of calc_loading_percent() to avoid printing a wrong result.

Fixes: a2178118 ("RDMA/hns: Add debugfs support for DCA")
Signed-off-by: default avatarYuyu Li <liyuyu6@huawei.com>
Signed-off-by: default avatarChengchang Tang <tangchengchang@huawei.com>
Signed-off-by: default avatarXinghai Cen <cenxinghai@h-partners.com>
parent c577c47e
Loading
Loading
Loading
Loading
+8 −2
Original line number Diff line number Diff line
@@ -243,8 +243,8 @@ static void dca_setup_pool_name(pid_t pid, bool is_kdca, char *name, int size)

static u64 calc_loading_percent(size_t total, size_t free, u32 *out_rem)
{
	u32 all_pages, used_pages, free_pages, scale;
	u64 percent = 0;
	u64 used_pages, scale, all_pages, free_pages;
	u64 percent = U64_MAX;
	u32 rem = 0;

	all_pages = total >> HNS_HW_PAGE_SHIFT;
@@ -270,6 +270,9 @@ static void dca_print_pool_stats(struct hns_roce_dca_ctx *ctx, pid_t pid,
	u32 rem = 0;

	percent = calc_loading_percent(ctx->total_size, ctx->free_size, &rem);
	if (percent == U64_MAX)
		return;

	dca_setup_pool_name(pid, is_kdca, name, sizeof(name));
	seq_printf(file, "%-10s %-16ld %-16ld %-16u %llu.%0*u\n", name,
		   ctx->total_size / KB, ctx->free_size / KB, ctx->free_mems,
@@ -422,6 +425,9 @@ static void dca_stats_ctx_mem_in_seqfile(struct hns_roce_dca_ctx *ctx,

	dca_ctx_stats_mem(ctx, &stats);
	percent = calc_loading_percent(stats.total_size, stats.free_size, &rem);
	if (percent == U64_MAX)
		return;

	seq_printf(file, DCA_STAT_NAME_FMT "%llu.%0*u\n", "Loading:", percent,
		   LOADING_PERCENT_SHIFT, rem);
	dca_ctx_print_mem_kb(file, "Total:", stats.total_size);