*** empty log message ***
[deliverable/binutils-gdb.git] / ld / emultempl / avrelf.em
CommitLineData
28c9d252 1# This shell script emits a C file. -*- C -*-
f96b4a7b 2# Copyright 2006, 2007
28c9d252
NC
3# Free Software Foundation, Inc.
4#
f96b4a7b 5# This file is part of the GNU Binutils.
28c9d252
NC
6#
7# This program is free software; you can redistribute it and/or modify
8# it under the terms of the GNU General Public License as published by
f96b4a7b 9# the Free Software Foundation; either version 3 of the License, or
28c9d252
NC
10# (at your option) any later version.
11#
12# This program is distributed in the hope that it will be useful,
13# but WITHOUT ANY WARRANTY; without even the implied warranty of
14# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15# GNU General Public License for more details.
16#
17# You should have received a copy of the GNU General Public License
18# along with this program; if not, write to the Free Software
f96b4a7b
NC
19# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20# MA 02110-1301, USA.
28c9d252 21
f96b4a7b
NC
22
23# This file is sourced from elf32.em, and defines extra avr-elf specific
24# routines. It is used to generate the trampolines for the avr6 family
25# of devices where one needs to address the issue that it is not possible
28c9d252
NC
26# to reach the whole program memory by using 16 bit pointers.
27
92b93329 28fragment <<EOF
28c9d252
NC
29
30#include "elf32-avr.h"
31#include "ldctor.h"
32
92b93329 33/* The fake file and it's corresponding section meant to hold
28c9d252
NC
34 the linker stubs if needed. */
35
36static lang_input_statement_type *stub_file;
37static asection *avr_stub_section;
38
39/* Variables set by the command-line parameters and transfered
40 to the bfd without use of global shared variables. */
41
42static bfd_boolean avr_no_stubs = FALSE;
43static bfd_boolean avr_debug_relax = FALSE;
44static bfd_boolean avr_debug_stubs = FALSE;
45static bfd_boolean avr_replace_call_ret_sequences = TRUE;
46static bfd_vma avr_pc_wrap_around = 0x10000000;
47
48/* Transfers information to the bfd frontend. */
49
50static void
51avr_elf_set_global_bfd_parameters (void)
52{
53 elf32_avr_setup_params (& link_info,
54 stub_file->the_bfd,
55 avr_stub_section,
56 avr_no_stubs,
57 avr_debug_stubs,
58 avr_debug_relax,
59 avr_pc_wrap_around,
60 avr_replace_call_ret_sequences);
61}
62
63
64/* Makes a conservative estimate of the trampoline section size that could
65 be corrected later on. */
66
67static void
68avr_elf_${EMULATION_NAME}_before_allocation (void)
69{
70 int ret;
71
72 gld${EMULATION_NAME}_before_allocation ();
73
74 /* We only need stubs for the avr6 family. */
75 if (strcmp ("${EMULATION_NAME}","avr6"))
76 avr_no_stubs = TRUE;
77
78 avr_elf_set_global_bfd_parameters ();
79
80 /* If generating a relocatable output file, then
81 we don't have to generate the trampolines. */
82 if (link_info.relocatable)
83 avr_no_stubs = TRUE;
84
85 if (avr_no_stubs)
86 return;
87
88 ret = elf32_avr_setup_section_lists (output_bfd, &link_info);
89
90 if (ret < 0)
91 einfo ("%X%P: can not setup the input section list: %E\n");
92
93 if (ret <= 0)
94 return;
95
96 /* Call into the BFD backend to do the real "stub"-work. */
97 if (! elf32_avr_size_stubs (output_bfd, &link_info, TRUE))
98 einfo ("%X%P: can not size stub section: %E\n");
99}
100
101/* This is called before the input files are opened. We create a new
102 fake input file to hold the stub section and generate the section itself. */
103
104static void
105avr_elf_create_output_section_statements (void)
106{
107 flagword flags;
108
109 stub_file = lang_add_input_file ("linker stubs",
110 lang_input_file_is_fake_enum,
111 NULL);
112
113 stub_file->the_bfd = bfd_create ("linker stubs", output_bfd);
114 if (stub_file->the_bfd == NULL
115 || !bfd_set_arch_mach (stub_file->the_bfd,
116 bfd_get_arch (output_bfd),
117 bfd_get_mach (output_bfd)))
118 {
119 einfo ("%X%P: can not create stub BFD %E\n");
120 return;
121 }
122
123 /* Now we add the stub section. */
124
125 avr_stub_section = bfd_make_section_anyway (stub_file->the_bfd,
126 ".trampolines");
127 if (avr_stub_section == NULL)
128 goto err_ret;
92b93329 129
28c9d252
NC
130 flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE
131 | SEC_HAS_CONTENTS | SEC_RELOC | SEC_IN_MEMORY | SEC_KEEP);
132 if (!bfd_set_section_flags (stub_file->the_bfd, avr_stub_section, flags))
133 goto err_ret;
134
135 avr_stub_section->alignment_power = 1;
92b93329 136
28c9d252
NC
137 ldlang_add_file (stub_file);
138
139 return;
140
141 err_ret:
142 einfo ("%X%P: can not make stub section: %E\n");
143 return;
144}
145
146/* Re-calculates the size of the stubs so that we won't waste space. */
147
148static void
149avr_elf_finish (void)
92b93329 150{
28c9d252
NC
151 if (!avr_no_stubs)
152 {
153 /* Now build the linker stubs. */
154 if (stub_file->the_bfd->sections != NULL)
155 {
156 /* Call again the trampoline analyzer to initialize the trampoline
157 stubs with the correct symbol addresses. Since there could have
158 been relaxation, the symbol addresses that were found during
159 first call may no longer be correct. */
160 if (!elf32_avr_size_stubs (output_bfd, &link_info, FALSE))
161 {
162 einfo ("%X%P: can not size stub section: %E\n");
163 return;
164 }
165
166 if (!elf32_avr_build_stubs (&link_info))
167 einfo ("%X%P: can not build stubs: %E\n");
168 }
169 }
170
171 gld${EMULATION_NAME}_finish ();
172}
173
174
175EOF
176
177
178PARSE_AND_LIST_PROLOGUE='
179
180#define OPTION_NO_CALL_RET_REPLACEMENT 301
181#define OPTION_PMEM_WRAP_AROUND 302
182#define OPTION_NO_STUBS 303
183#define OPTION_DEBUG_STUBS 304
184#define OPTION_DEBUG_RELAX 305
185'
186
187PARSE_AND_LIST_LONGOPTS='
92b93329 188 { "no-call-ret-replacement", no_argument,
28c9d252 189 NULL, OPTION_NO_CALL_RET_REPLACEMENT},
92b93329 190 { "pmem-wrap-around", required_argument,
28c9d252 191 NULL, OPTION_PMEM_WRAP_AROUND},
92b93329 192 { "no-stubs", no_argument,
28c9d252 193 NULL, OPTION_NO_STUBS},
92b93329 194 { "debug-stubs", no_argument,
28c9d252 195 NULL, OPTION_DEBUG_STUBS},
92b93329 196 { "debug-relax", no_argument,
28c9d252
NC
197 NULL, OPTION_DEBUG_RELAX},
198'
199
200PARSE_AND_LIST_OPTIONS='
442996ee
AM
201 fprintf (file, _(" --pmem-wrap-around=<val> "
202 "Make the linker relaxation machine assume that a\n"
203 " "
204 " program counter wrap-around occures at address\n"
205 " "
206 " <val>. Supported values: 8k, 16k, 32k and 64k.\n"));
207 fprintf (file, _(" --no-call-ret-replacement "
208 "The relaxation machine normally will\n"
209 " "
210 " substitute two immediately following call/ret\n"
211 " "
212 " instructions by a single jump instruction.\n"
213 " "
214 " This option disables this optimization.\n"));
215 fprintf (file, _(" --no-stubs "
216 "If the linker detects to attempt to access\n"
217 " "
218 " an instruction beyond 128k by a reloc that\n"
219 " "
220 " is limited to 128k max, it inserts a jump\n"
221 " "
222 " stub. You can de-active this with this switch.\n"));
223 fprintf (file, _(" --debug-stubs "
224 "Used for debugging avr-ld.\n"));
225 fprintf (file, _(" --debug-relax "
226 "Used for debugging avr-ld.\n"));
28c9d252
NC
227'
228
229PARSE_AND_LIST_ARGS_CASES='
230
231 case OPTION_PMEM_WRAP_AROUND:
92b93329 232 {
28c9d252
NC
233 /* This variable is defined in the bfd library. */
234 if ((!strcmp (optarg,"32k")) || (!strcmp (optarg,"32K")))
235 avr_pc_wrap_around = 32768;
2a69000b
DC
236 else if ((!strcmp (optarg,"8k")) || (!strcmp (optarg,"8K")))
237 avr_pc_wrap_around = 8192;
28c9d252
NC
238 else if ((!strcmp (optarg,"16k")) || (!strcmp (optarg,"16K")))
239 avr_pc_wrap_around = 16384;
240 else if ((!strcmp (optarg,"64k")) || (!strcmp (optarg,"64K")))
241 avr_pc_wrap_around = 0x10000;
242 else
243 return FALSE;
244 }
245 break;
246
247 case OPTION_DEBUG_STUBS:
248 avr_debug_stubs = TRUE;
249 break;
250
251 case OPTION_DEBUG_RELAX:
252 avr_debug_relax = TRUE;
253 break;
254
255 case OPTION_NO_STUBS:
256 avr_no_stubs = TRUE;
257 break;
258
259 case OPTION_NO_CALL_RET_REPLACEMENT:
260 {
261 /* This variable is defined in the bfd library. */
262 avr_replace_call_ret_sequences = FALSE;
263 }
264 break;
265'
266
267#
268# Put these extra avr-elf routines in ld_${EMULATION_NAME}_emulation
269#
270LDEMUL_BEFORE_ALLOCATION=avr_elf_${EMULATION_NAME}_before_allocation
271LDEMUL_FINISH=avr_elf_finish
272LDEMUL_CREATE_OUTPUT_SECTION_STATEMENTS=avr_elf_create_output_section_statements
This page took 0.091164 seconds and 4 git commands to generate.