summaryrefslogtreecommitdiffstats
path: root/libunwind/src
diff options
context:
space:
mode:
authorMartin Storsjo <martin@martin.st>2017-10-24 07:16:40 +0000
committerMartin Storsjo <martin@martin.st>2017-10-24 07:16:40 +0000
commitd3abd15d8cd9455bc7b1eeb2e6f4b4d0047a0dd6 (patch)
treec4571e60744ada713da45a7b681e1628606f0ff0 /libunwind/src
parent2555e41b4e933c01bb7fe651ad8520b35d9eeaca (diff)
downloadbcm5719-llvm-d3abd15d8cd9455bc7b1eeb2e6f4b4d0047a0dd6.tar.gz
bcm5719-llvm-d3abd15d8cd9455bc7b1eeb2e6f4b4d0047a0dd6.zip
Add missing checks for register number
Most other cases that touch savedRegisters[reg] have got this check, but these three seemed to lack it. Differential Revision: https://reviews.llvm.org/D39206 llvm-svn: 316415
Diffstat (limited to 'libunwind/src')
-rw-r--r--libunwind/src/DwarfParser.hpp19
1 files changed, 19 insertions, 0 deletions
diff --git a/libunwind/src/DwarfParser.hpp b/libunwind/src/DwarfParser.hpp
index 3c98d304fda..d45ad49c5db 100644
--- a/libunwind/src/DwarfParser.hpp
+++ b/libunwind/src/DwarfParser.hpp
@@ -605,6 +605,13 @@ bool CFI_Parser<A>::parseInstructions(A &addressSpace, pint_t instructions,
break;
case DW_CFA_val_offset:
reg = addressSpace.getULEB128(p, instructionsEnd);
+ if (reg > kMaxRegisterNumber) {
+ fprintf(stderr,
+ "malformed DW_CFA_val_offset DWARF unwind, reg (%" PRIu64
+ ") out of range\n",
+ reg);
+ return false;
+ }
offset = (int64_t)addressSpace.getULEB128(p, instructionsEnd)
* cieInfo.dataAlignFactor;
results->savedRegisters[reg].location = kRegisterOffsetFromCFA;
@@ -668,6 +675,12 @@ bool CFI_Parser<A>::parseInstructions(A &addressSpace, pint_t instructions,
switch (opcode & 0xC0) {
case DW_CFA_offset:
reg = operand;
+ if (reg > kMaxRegisterNumber) {
+ fprintf(stderr, "malformed DW_CFA_offset DWARF unwind, reg (%" PRIu64
+ ") out of range\n",
+ reg);
+ return false;
+ }
offset = (int64_t)addressSpace.getULEB128(p, instructionsEnd)
* cieInfo.dataAlignFactor;
results->savedRegisters[reg].location = kRegisterInCFA;
@@ -682,6 +695,12 @@ bool CFI_Parser<A>::parseInstructions(A &addressSpace, pint_t instructions,
break;
case DW_CFA_restore:
reg = operand;
+ if (reg > kMaxRegisterNumber) {
+ fprintf(stderr, "malformed DW_CFA_restore DWARF unwind, reg (%" PRIu64
+ ") out of range\n",
+ reg);
+ return false;
+ }
results->savedRegisters[reg] = initialState.savedRegisters[reg];
_LIBUNWIND_TRACE_DWARF("DW_CFA_restore(reg=%" PRIu64 ")\n",
static_cast<uint64_t>(operand));
OpenPOWER on IntegriCloud