Index: lib/Target/ARM/MCTargetDesc/ARMAsmBackend.cpp =================================================================== --- lib/Target/ARM/MCTargetDesc/ARMAsmBackend.cpp +++ lib/Target/ARM/MCTargetDesc/ARMAsmBackend.cpp @@ -518,9 +518,11 @@ return swapHalfWords(out, Endian == support::little); } case ARM::fixup_arm_thumb_bl: { - // FIXME: We get both thumb1 and thumb2 in here, so we can only check for - // the less strict thumb2 value. - if (!isInt<26>(Value - 4)) { + if (!isInt<25>(Value - 4) || + (!STI.getFeatureBits()[ARM::FeatureThumb2] && + !STI.getFeatureBits()[ARM::HasV8MBaselineOps] && + !STI.getFeatureBits()[ARM::HasV6MOps] && + !isInt<23>(Value - 4))) { Ctx.reportError(Fixup.getLoc(), "Relocation out of range"); return 0; } Index: test/MC/ARM/thumb-branches.s =================================================================== --- test/MC/ARM/thumb-branches.s +++ test/MC/ARM/thumb-branches.s @@ -1,43 +1,71 @@ -@ RUN: not llvm-mc %s -triple thumbv5-linux-gnueabi -filetype=obj -o /dev/null 2>&1 | FileCheck %s +@ RUN: not llvm-mc %s -triple thumbv7-linux-gnueabi -filetype=obj -o /dev/null 2>&1 | FileCheck %s +@ RUN: not llvm-mc %s -triple thumbv8-m.baseline-none-eabi -filetype=obj -o /dev/null 2>&1 | FileCheck %s +@ RUN: not llvm-mc %s -triple thumbv8-m.mainline-none-eabi -filetype=obj -o /dev/null 2>&1 | FileCheck %s +@ RUN: not llvm-mc %s -triple thumbv6m-none-eabi -filetype=obj -o /dev/null 2>&1 | FileCheck %s +@ RUN: not llvm-mc %s -triple thumbv5-linux-gnueabi -filetype=obj -o /dev/null 2>&1 | FileCheck -check-prefix=CHECKSHORT %s + +// Thumb BL has range +- 4 Megabytes if CPU does not support Thumb2 or does not +// have v8-M baseline ops, it is +- 16 Megabytes otherwise. .code 16 + bl shortend + .space 0x3fffff +shortend: +// CHECKSHORT-NOT: error +// CHECKSHORT: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range + bl shortend2 + .space 0x400000 +shortend2: +// CHECKSHORT: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range bl end - .space 0x1ffffff + .space 0xffffff end: - bl end2 - .space 0x1ffffff + .space 0xffffff .global end2 end2: bl end3 - .space 0x2000000 + .space 0x1000000 .global end3 end3: // CHECK-NOT: error +// CHECKSHORT-NOT: error +// CHECKSHORT: [[@LINE+2]]:{{[0-9]}}: error: Relocation out of range // CHECK: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range bl end4 -// CHECK-NOT: error - .space 0x2000000 + .space 0x1000000 end4: +shortstart1: + .space 0x3ffffc + bl shortstart1 + +shortstart2: + .space 0x400000 +// CHECKSHORT: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range + bl shortstart2 + start1: - .space 0x1fffffc + .space 0xfffffc +// CHECKSHORT: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range bl start1 .global start2 start2: - .space 0x1fffffc + .space 0xfffffc bl start2 .global start3 start3: - .space 0x1fffffd + .space 0xfffffd bl start3 +// CHECK-NOT: error start4: - .space 0x1fffffd -// CHECK: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range + .space 0xfffffd +// CHECK: [[@LINE+2]]:{{[0-9]}}: error: Relocation out of range +// CHECKSHORT: [[@LINE+1]]:{{[0-9]}}: error: Relocation out of range bl start4