From eb8ec12b239714f70039d59b0c9e7b73d3f10b58 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Sch=C3=BCrmann?= Date: Thu, 2 Sep 2021 15:42:56 +0200 Subject: [PATCH] aco/ra: Fix potential out-of-bounds array accesses. Reviewed-by: Rhys Perry Part-of: --- src/amd/compiler/aco_register_allocation.cpp | 24 +++++++++++--------- 1 file changed, 13 insertions(+), 11 deletions(-) diff --git a/src/amd/compiler/aco_register_allocation.cpp b/src/amd/compiler/aco_register_allocation.cpp index e19eb0bb2df..d57c482509f 100644 --- a/src/amd/compiler/aco_register_allocation.cpp +++ b/src/amd/compiler/aco_register_allocation.cpp @@ -910,7 +910,7 @@ get_reg_simple(ra_ctx& ctx, RegisterFile& reg_file, DefInfo info) if (rc.is_subdword()) { for (std::pair>& entry : reg_file.subdword_regs) { assert(reg_file[PhysReg{entry.first}] == 0xF0000000); - if (!bounds.contains(PhysReg{entry.first})) + if (!bounds.contains({PhysReg{entry.first}, rc.size()})) continue; for (unsigned i = 0; i < 4; i += info.stride) { @@ -1434,19 +1434,21 @@ is_mimg_vaddr_intact(ra_ctx& ctx, RegisterFile& reg_file, Instruction* instr) if (ctx.assignments[op.tempId()].assigned) { PhysReg reg = ctx.assignments[op.tempId()].reg; - if (first.reg() != 512 && reg != first.advance(i * 4)) - return false; /* not at the best position */ - - if ((reg.reg() - 256) < i) - return false; /* no space for previous operands */ - - first = reg.advance(i * -4); - } else if (first.reg() != 512) { + if (first.reg() == 512) { + PhysRegInterval bounds = get_reg_bounds(ctx.program, RegType::vgpr); + first = reg.advance(i * -4); + PhysRegInterval vec = PhysRegInterval{first, instr->operands.size() - 3u}; + if (!bounds.contains(vec)) /* not enough space for other operands */ + return false; + } else { + if (reg != first.advance(i * 4)) /* not at the best position */ + return false; + } + } else { /* If there's an unexpected temporary, this operand is unlikely to be * placed in the best position. */ - unsigned id = reg_file.get_id(first.advance(i * 4)); - if (id && id != op.tempId()) + if (first.reg() != 512 && reg_file.test(first.advance(i * 4), 4)) return false; } }