dba7620b7e1ce4578831905589253d85d6590526
[packages/trusty/cirros-testvm.git] / cirros-testvm / src-cirros / buildroot-2015.05 / package / binutils / 2.23.2 / 904-Fix-call8-call-target-out-of-range-xtensa-ld-relaxation.patch
1 From 7fc39194f8fb48914c995f8ec3826d50086f1ec0 Mon Sep 17 00:00:00 2001
2 From: Sterling Augustine <augustine.sterling@gmail.com>
3 Date: Tue, 25 Jan 2011 13:59:13 -0800
4 Subject: [PATCH] Fix 'call8: call target out of range' xtensa ld relaxation
5  bug
6
7 During link-time relaxation distance between cross-section call site and
8 its target may grow, producing 'call target out of range' error for
9 relaxed calls. Be more conservative when calculating whether or not a
10 callx can be converted to a straight call.
11
12 2014-09-23  Sterling Augustine  <augustine.sterling@gmail.com>
13
14 bfd/
15     * elf32-xtensa.c (is_resolvable_asm_expansion): for cross-section
16     call relaxation use furthermost addresses where call source and
17     destination can be to check whether it's in the range of a direct
18     call.
19
20 Signed-off-by: Max Filippov <jcmvbkbc@gmail.com>
21 ---
22  bfd/elf32-xtensa.c | 41 +++++++++++++++++++++++++++++++++++++----
23  1 file changed, 37 insertions(+), 4 deletions(-)
24
25 diff --git a/bfd/elf32-xtensa.c b/bfd/elf32-xtensa.c
26 index 09862e3..e32496a 100644
27 --- a/bfd/elf32-xtensa.c
28 +++ b/bfd/elf32-xtensa.c
29 @@ -7124,10 +7124,43 @@ is_resolvable_asm_expansion (bfd *abfd,
30           || is_reloc_sym_weak (abfd, irel)))
31      return FALSE;
32  
33 -  self_address = (sec->output_section->vma
34 -                 + sec->output_offset + irel->r_offset + 3);
35 -  dest_address = (target_sec->output_section->vma
36 -                 + target_sec->output_offset + target_offset);
37 +  if (target_sec->output_section != sec->output_section)
38 +    {
39 +      /* If the two sections are sufficiently far away that relaxation
40 +        might take the call out of range, we can't simplify.  For
41 +        example, a positive displacement call into another memory
42 +        could get moved to a lower address due to literal removal,
43 +        but the destination won't move, and so the displacment might
44 +        get larger.
45 +
46 +        If the displacement is negative, assume the destination could
47 +        move as far back as the start of the output section.  The
48 +        self_address will be at least as far into the output section
49 +        as it is prior to relaxation.
50 +
51 +        If the displacement is postive, assume the destination will be in
52 +        it's pre-relaxed location (because relaxation only makes sections
53 +        smaller).  The self_address could go all the way to the beginning
54 +        of the output section.  */
55 +
56 +      dest_address = target_sec->output_section->vma;
57 +      self_address = sec->output_section->vma;
58 +
59 +      if (sec->output_section->vma > target_sec->output_section->vma)
60 +       self_address += sec->output_offset + irel->r_offset + 3;
61 +      else
62 +       dest_address += bfd_get_section_limit (abfd, target_sec->output_section);
63 +      /* Call targets should be four-byte aligned.  */
64 +      dest_address = (dest_address + 3) & ~3;
65 +    }
66 +  else
67 +    {
68 +
69 +      self_address = (sec->output_section->vma
70 +                     + sec->output_offset + irel->r_offset + 3);
71 +      dest_address = (target_sec->output_section->vma
72 +                     + target_sec->output_offset + target_offset);
73 +    }
74        
75    *is_reachable_p = pcrel_reloc_fits (direct_call_opcode, 0,
76                                       self_address, dest_address);
77 -- 
78 1.8.1.4
79