Blame view

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