1 # This shell script emits a C file. -*- C -*- 2 # It does some substitutions. 3 fragment <<EOF 4 /* intel coff loader emulation specific stuff 5 Copyright (C) 1991-2014 Free Software Foundation, Inc. 6 Written by Steve Chamberlain steve (a] cygnus.com 7 8 This file is part of the GNU Binutils. 9 10 This program is free software; you can redistribute it and/or modify 11 it under the terms of the GNU General Public License as published by 12 the Free Software Foundation; either version 3 of the License, or 13 (at your option) any later version. 14 15 This program is distributed in the hope that it will be useful, 16 but WITHOUT ANY WARRANTY; without even the implied warranty of 17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 GNU General Public License for more details. 19 20 You should have received a copy of the GNU General Public License 21 along with this program; if not, write to the Free Software 22 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, 23 MA 02110-1301, USA. */ 24 25 #include "sysdep.h" 26 #include "libiberty.h" 27 #include "bfd.h" 28 #include "bfdlink.h" 29 30 /*#include "archures.h"*/ 31 #include "ld.h" 32 #include "ldmain.h" 33 #include "ldmisc.h" 34 #include "ldexp.h" 35 #include "ldlang.h" 36 #include "ldfile.h" 37 #include "ldemul.h" 38 39 typedef struct lib_list { 40 char *name; 41 struct lib_list *next; 42 } lib_list_type; 43 44 static lib_list_type *hll_list; 45 static lib_list_type **hll_list_tail = &hll_list; 46 47 static lib_list_type *syslib_list; 48 static lib_list_type **syslib_list_tail = &syslib_list; 49 50 51 static void 52 append (lib_list_type ***list, char *name) 53 { 54 lib_list_type *element = (lib_list_type *) xmalloc (sizeof (lib_list_type)); 55 56 element->name = name; 57 element->next = (lib_list_type *) NULL; 58 **list = element; 59 *list = &element->next; 60 61 } 62 63 static bfd_boolean had_hll = FALSE; 64 static bfd_boolean had_hll_name = FALSE; 65 66 static void 67 lnk960_hll (char *name) 68 { 69 had_hll = TRUE; 70 if (name != (char *) NULL) 71 { 72 had_hll_name = TRUE; 73 append (&hll_list_tail, name); 74 } 75 } 76 77 static void 78 lnk960_syslib (char *name) 79 { 80 append (&syslib_list_tail, name); 81 } 82 83 84 static void 85 lnk960_before_parse (void) 86 { 87 char *name = getenv ("I960BASE"); 88 89 if (name == (char *) NULL) 90 { 91 name = getenv("G960BASE"); 92 if (name == (char *) NULL) 93 einfo ("%P%F I960BASE and G960BASE not set\n"); 94 } 95 96 ldfile_add_library_path (concat (name, "/lib", (const char *) NULL), FALSE); 97 ldfile_output_architecture = bfd_arch_i960; 98 ldfile_output_machine = bfd_mach_i960_core; 99 } 100 101 static void 102 add_on (lib_list_type *list, lang_input_file_enum_type search) 103 { 104 while (list) 105 { 106 lang_add_input_file (list->name, search, (char *) NULL); 107 list = list->next; 108 } 109 } 110 111 static void 112 lnk960_after_parse (void) 113 { 114 /* If there has been no arch, default to -KB */ 115 if (ldfile_output_machine_name[0] == 0) 116 ldfile_add_arch ("KB"); 117 118 /* if there has been no hll list then add our own */ 119 120 if (had_hll && !had_hll_name) 121 { 122 append (&hll_list_tail, "cg"); 123 if (ldfile_output_machine == bfd_mach_i960_ka_sa 124 || ldfile_output_machine == bfd_mach_i960_ca) 125 append (&hll_list_tail, "fpg"); 126 } 127 128 add_on (hll_list, lang_input_file_is_l_enum); 129 add_on (syslib_list, lang_input_file_is_search_file_enum); 130 } 131 132 static void 133 lnk960_after_allocation (void) 134 { 135 if (!link_info.relocatable) 136 { 137 lang_abs_symbol_at_end_of (".text", "_etext"); 138 lang_abs_symbol_at_end_of (".data", "_edata"); 139 lang_abs_symbol_at_beginning_of (".bss", "_bss_start"); 140 lang_abs_symbol_at_end_of (".bss", "_end"); 141 } 142 } 143 144 145 static struct 146 { 147 unsigned long number; 148 char *name; 149 } 150 machine_table[] = 151 { 152 { bfd_mach_i960_core ,"CORE" }, 153 { bfd_mach_i960_kb_sb ,"KB" }, 154 { bfd_mach_i960_kb_sb ,"SB" }, 155 { bfd_mach_i960_mc ,"MC" }, 156 { bfd_mach_i960_xa ,"XA" }, 157 { bfd_mach_i960_ca ,"CA" }, 158 { bfd_mach_i960_ka_sa ,"KA" }, 159 { bfd_mach_i960_ka_sa ,"SA" }, 160 { bfd_mach_i960_jx ,"JX" }, 161 { bfd_mach_i960_hx ,"HX" }, 162 163 { bfd_mach_i960_core ,"core" }, 164 { bfd_mach_i960_kb_sb ,"kb" }, 165 { bfd_mach_i960_kb_sb ,"sb" }, 166 { bfd_mach_i960_mc ,"mc" }, 167 { bfd_mach_i960_xa ,"xa" }, 168 { bfd_mach_i960_ca ,"ca" }, 169 { bfd_mach_i960_ka_sa ,"ka" }, 170 { bfd_mach_i960_ka_sa ,"sa" }, 171 { bfd_mach_i960_jx ,"jx" }, 172 { bfd_mach_i960_hx ,"hx" }, 173 174 { 0, (char *) NULL } 175 }; 176 177 static void 178 lnk960_set_output_arch (void) 179 { 180 /* Set the output architecture and machine if possible */ 181 unsigned int i; 182 ldfile_output_machine = bfd_mach_i960_core; 183 for (i= 0; machine_table[i].name != (char*) NULL; i++) 184 { 185 if (strcmp (ldfile_output_machine_name, machine_table[i].name) == 0) 186 { 187 ldfile_output_machine = machine_table[i].number; 188 break; 189 } 190 } 191 bfd_set_arch_mach (link_info.output_bfd, ldfile_output_architecture, 192 ldfile_output_machine); 193 } 194 195 static char * 196 lnk960_choose_target (int argc ATTRIBUTE_UNUSED, char **argv ATTRIBUTE_UNUSED) 197 { 198 char *from_outside = getenv (TARGET_ENVIRON); 199 if (from_outside != (char *) NULL) 200 return from_outside; 201 #ifdef LNK960_LITTLE 202 return "coff-Intel-little"; 203 #else 204 return "coff-Intel-big"; 205 #endif 206 } 207 208 static char * 209 lnk960_get_script (int *isfile) 210 EOF 211 212 if test x"$COMPILE_IN" = xyes 213 then 214 # Scripts compiled in. 215 216 # sed commands to quote an ld script as a C string. 217 sc="-f stringify.sed" 218 219 fragment <<EOF 220 { 221 *isfile = 0; 222 223 if (link_info.relocatable && config.build_constructors) 224 return 225 EOF 226 sed $sc ldscripts/${EMULATION_NAME}.xu >> e${EMULATION_NAME}.c 227 echo ' ; else if (link_info.relocatable) return' >> e${EMULATION_NAME}.c 228 sed $sc ldscripts/${EMULATION_NAME}.xr >> e${EMULATION_NAME}.c 229 echo ' ; else if (!config.text_read_only) return' >> e${EMULATION_NAME}.c 230 sed $sc ldscripts/${EMULATION_NAME}.xbn >> e${EMULATION_NAME}.c 231 echo ' ; else if (!config.magic_demand_paged) return' >> e${EMULATION_NAME}.c 232 sed $sc ldscripts/${EMULATION_NAME}.xn >> e${EMULATION_NAME}.c 233 echo ' ; else return' >> e${EMULATION_NAME}.c 234 sed $sc ldscripts/${EMULATION_NAME}.x >> e${EMULATION_NAME}.c 235 echo '; }' >> e${EMULATION_NAME}.c 236 237 else 238 # Scripts read from the filesystem. 239 240 fragment <<EOF 241 { 242 *isfile = 1; 243 244 if (link_info.relocatable && config.build_constructors) 245 return "ldscripts/${EMULATION_NAME}.xu"; 246 else if (link_info.relocatable) 247 return "ldscripts/${EMULATION_NAME}.xr"; 248 else if (!config.text_read_only) 249 return "ldscripts/${EMULATION_NAME}.xbn"; 250 else if (!config.magic_demand_paged) 251 return "ldscripts/${EMULATION_NAME}.xn"; 252 else 253 return "ldscripts/${EMULATION_NAME}.x"; 254 } 255 EOF 256 257 fi 258 259 fragment <<EOF 260 261 struct ld_emulation_xfer_struct ld_lnk960_emulation = 262 { 263 lnk960_before_parse, 264 lnk960_syslib, 265 lnk960_hll, 266 lnk960_after_parse, 267 after_open_default, 268 lnk960_after_allocation, 269 lnk960_set_output_arch, 270 lnk960_choose_target, 271 before_allocation_default, 272 lnk960_get_script, 273 "lnk960", 274 "", 275 finish_default, 276 NULL, /* create output section statements */ 277 NULL, /* open dynamic archive */ 278 NULL, /* place orphan */ 279 NULL, /* set symbols */ 280 NULL, /* parse args */ 281 NULL, /* add_options */ 282 NULL, /* handle_option */ 283 NULL, /* unrecognized file */ 284 NULL, /* list options */ 285 NULL, /* recognized file */ 286 NULL, /* find_potential_libraries */ 287 NULL, /* new_vers_pattern */ 288 NULL /* extra_map_file_text */ 289 }; 290 EOF 291