| 1 | # This shell script emits a C file. -*- C -*-
|
|---|
| 2 | # It does some substitutions.
|
|---|
| 3 | # Derived from generic.em and partialy from emx's ld.c
|
|---|
| 4 | cat >e${EMULATION_NAME}.c <<EOF
|
|---|
| 5 | /* This file is is generated by a shell script. DO NOT EDIT! */
|
|---|
| 6 |
|
|---|
| 7 | /* emulate the original gld for the given ${EMULATION_NAME}
|
|---|
| 8 | Copyright (C) 1991, 1993 Free Software Foundation, Inc.
|
|---|
| 9 | Written by Steve Chamberlain steve@cygnus.com
|
|---|
| 10 |
|
|---|
| 11 | This file is part of GLD, the Gnu Linker.
|
|---|
| 12 |
|
|---|
| 13 | This program is free software; you can redistribute it and/or modify
|
|---|
| 14 | it under the terms of the GNU General Public License as published by
|
|---|
| 15 | the Free Software Foundation; either version 2 of the License, or
|
|---|
| 16 | (at your option) any later version.
|
|---|
| 17 |
|
|---|
| 18 | This program is distributed in the hope that it will be useful,
|
|---|
| 19 | but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|---|
| 20 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|---|
| 21 | GNU General Public License for more details.
|
|---|
| 22 |
|
|---|
| 23 | You should have received a copy of the GNU General Public License
|
|---|
| 24 | along with this program; if not, write to the Free Software
|
|---|
| 25 | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
|
|---|
| 26 |
|
|---|
| 27 | #define TARGET_IS_${EMULATION_NAME}
|
|---|
| 28 |
|
|---|
| 29 | #include "bfd.h"
|
|---|
| 30 | #include "sysdep.h"
|
|---|
| 31 | #include "libiberty.h"
|
|---|
| 32 | #include "getopt.h"
|
|---|
| 33 | #include "obstack.h"
|
|---|
| 34 | #include "bfdlink.h"
|
|---|
| 35 |
|
|---|
| 36 | #include "ld.h"
|
|---|
| 37 | #include "ldmain.h"
|
|---|
| 38 | #include "ldfile.h"
|
|---|
| 39 | #include "ldemul.h"
|
|---|
| 40 | #include "ldmisc.h"
|
|---|
| 41 | #include "ldexp.h"
|
|---|
| 42 | #include "ldlang.h"
|
|---|
| 43 | #include "ldctor.h"
|
|---|
| 44 | #include "ldgram.h"
|
|---|
| 45 |
|
|---|
| 46 | #ifdef ANSI_PROTOTYPES
|
|---|
| 47 | #include <stdarg.h>
|
|---|
| 48 | #else
|
|---|
| 49 | #include <varargs.h>
|
|---|
| 50 | #endif
|
|---|
| 51 |
|
|---|
| 52 | static void gld${EMULATION_NAME}_before_parse PARAMS ((void));
|
|---|
| 53 | static char *gld${EMULATION_NAME}_get_script PARAMS ((int *isfile));
|
|---|
| 54 | static int gld${EMULATION_NAME}_parse_args PARAMS ((int argc, char **argv));
|
|---|
| 55 | static bfd_boolean gld${EMULATION_NAME}_unrecognized_file PARAMS ((lang_input_statement_type *entry));
|
|---|
| 56 |
|
|---|
| 57 |
|
|---|
| 58 | static int parse PARAMS ((char *arg, char *format, char *error));
|
|---|
| 59 |
|
|---|
| 60 |
|
|---|
| 61 | static void
|
|---|
| 62 | gld${EMULATION_NAME}_before_parse(void)
|
|---|
| 63 | {
|
|---|
| 64 | ldfile_set_output_arch ("`echo ${ARCH}`");
|
|---|
| 65 | output_filename = "a.out";
|
|---|
| 66 | }
|
|---|
| 67 |
|
|---|
| 68 | static char *
|
|---|
| 69 | gld${EMULATION_NAME}_get_script(isfile)
|
|---|
| 70 | int *isfile;
|
|---|
| 71 | EOF
|
|---|
| 72 |
|
|---|
| 73 | if test -n "$COMPILE_IN"
|
|---|
| 74 | then
|
|---|
| 75 | # Scripts compiled in.
|
|---|
| 76 |
|
|---|
| 77 | # sed commands to quote an ld script as a C string.
|
|---|
| 78 | # bird: stringify.sed is in current directory.
|
|---|
| 79 | sc="-f stringify.sed"
|
|---|
| 80 |
|
|---|
| 81 | #cat >>e${EMULATION_NAME}.c <<EOF
|
|---|
| 82 | #{
|
|---|
| 83 | # *isfile = 0;
|
|---|
| 84 | #
|
|---|
| 85 | # if (link_info.relocateable == TRUE && config.build_constructors == TRUE)
|
|---|
| 86 | # return
|
|---|
| 87 | #EOF
|
|---|
| 88 | #sed $sc ldscripts/${EMULATION_NAME}.xu >> e${EMULATION_NAME}.c
|
|---|
| 89 | #echo ' ; else if (link_info.relocateable == TRUE) return' >> e${EMULATION_NAME}.c
|
|---|
| 90 | #sed $sc ldscripts/${EMULATION_NAME}.xr >> e${EMULATION_NAME}.c
|
|---|
| 91 | #echo ' ; else if (!config.text_read_only) return' >> e${EMULATION_NAME}.c
|
|---|
| 92 | #sed $sc ldscripts/${EMULATION_NAME}.xbn >> e${EMULATION_NAME}.c
|
|---|
| 93 | #echo ' ; else if (!config.magic_demand_paged) return' >> e${EMULATION_NAME}.c
|
|---|
| 94 | #sed $sc ldscripts/${EMULATION_NAME}.xn >> e${EMULATION_NAME}.c
|
|---|
| 95 | #echo ' ; else return' >> e${EMULATION_NAME}.c
|
|---|
| 96 | #sed $sc ldscripts/${EMULATION_NAME}.x >> e${EMULATION_NAME}.c
|
|---|
| 97 | #echo '; }' >> e${EMULATION_NAME}.c
|
|---|
| 98 |
|
|---|
| 99 | cat >>e${EMULATION_NAME}.c <<EOF
|
|---|
| 100 | {
|
|---|
| 101 | *isfile = 0;
|
|---|
| 102 |
|
|---|
| 103 | EOF
|
|---|
| 104 | echo ' if (!config.text_read_only) return' >> e${EMULATION_NAME}.c
|
|---|
| 105 | sed $sc ldscripts/${EMULATION_NAME}.xbn >> e${EMULATION_NAME}.c
|
|---|
| 106 | echo ' ; else if (!config.magic_demand_paged) return' >> e${EMULATION_NAME}.c
|
|---|
| 107 | sed $sc ldscripts/${EMULATION_NAME}.xn >> e${EMULATION_NAME}.c
|
|---|
| 108 | echo ' ; else return' >> e${EMULATION_NAME}.c
|
|---|
| 109 | sed $sc ldscripts/${EMULATION_NAME}.x >> e${EMULATION_NAME}.c
|
|---|
| 110 | echo '; }' >> e${EMULATION_NAME}.c
|
|---|
| 111 |
|
|---|
| 112 | else
|
|---|
| 113 | # Scripts read from the filesystem.
|
|---|
| 114 |
|
|---|
| 115 | cat >>e${EMULATION_NAME}.c <<EOF
|
|---|
| 116 | {
|
|---|
| 117 | *isfile = 1;
|
|---|
| 118 |
|
|---|
| 119 | if (link_info.relocateable == TRUE && config.build_constructors == TRUE)
|
|---|
| 120 | return "ldscripts/${EMULATION_NAME}.xu";
|
|---|
| 121 | else if (link_info.relocateable == TRUE)
|
|---|
| 122 | return "ldscripts/${EMULATION_NAME}.xr";
|
|---|
| 123 | else if (!config.text_read_only)
|
|---|
| 124 | return "ldscripts/${EMULATION_NAME}.xbn";
|
|---|
| 125 | else if (!config.magic_demand_paged)
|
|---|
| 126 | return "ldscripts/${EMULATION_NAME}.xn";
|
|---|
| 127 | else
|
|---|
| 128 | return "ldscripts/${EMULATION_NAME}.x";
|
|---|
| 129 | }
|
|---|
| 130 | EOF
|
|---|
| 131 |
|
|---|
| 132 | fi
|
|---|
| 133 |
|
|---|
| 134 | cat >>e${EMULATION_NAME}.c <<EOF
|
|---|
| 135 |
|
|---|
| 136 | extern char *program_name;
|
|---|
| 137 |
|
|---|
| 138 | /* Report a fatal error.
|
|---|
| 139 | FMT is a printf format string and ARG is one arg for it. */
|
|---|
| 140 |
|
|---|
| 141 | static void fatal VPARAMS ((char *fmt, ...))
|
|---|
| 142 | {
|
|---|
| 143 | VA_OPEN (arg, fmt);
|
|---|
| 144 | VA_FIXEDARG (arg, char *, fmt);
|
|---|
| 145 |
|
|---|
| 146 | fprintf (stderr, "%s: ", program_name);
|
|---|
| 147 | vfprintf (stderr, fmt, arg);
|
|---|
| 148 | VA_CLOSE (arg);
|
|---|
| 149 | fprintf (stderr, "\n");
|
|---|
| 150 | xexit (1);
|
|---|
| 151 | }
|
|---|
| 152 |
|
|---|
| 153 | /* Parse the string ARG using scanf format FORMAT, and return the result.
|
|---|
| 154 | If it does not parse, report fatal error
|
|---|
| 155 | generating the error message using format string ERROR and ARG as arg. */
|
|---|
| 156 |
|
|---|
| 157 | static int
|
|---|
| 158 | parse (arg, format, error)
|
|---|
| 159 | char *arg, *format, *error;
|
|---|
| 160 | {
|
|---|
| 161 | int x;
|
|---|
| 162 | if (1 != sscanf (arg, format, &x))
|
|---|
| 163 | fatal (error, arg);
|
|---|
| 164 | return x;
|
|---|
| 165 | }
|
|---|
| 166 |
|
|---|
| 167 | #define OPT_ZEXE 9990
|
|---|
| 168 | #define OPT_ZSTACK 9991
|
|---|
| 169 | #define OPT_ZMAP 9992
|
|---|
| 170 | #define OPT_ZNODEMANGLE 9993
|
|---|
| 171 | #define OPT_ZDEMANGLEPROTO 9994
|
|---|
| 172 | #define OPT_ZEMX32 9995
|
|---|
| 173 | #define OPT_ZRSX32 9996
|
|---|
| 174 | #define OPT_ZWIN32 9997
|
|---|
| 175 |
|
|---|
| 176 | static struct option longopts[] =
|
|---|
| 177 | {
|
|---|
| 178 | {"Zexe", 0, 0, OPT_ZEXE}, /* Create .exe file, touch 'output file' */
|
|---|
| 179 | {"Zstack", 1, 0, OPT_ZSTACK}, /* Set stack size */
|
|---|
| 180 | {"Zmap", 2, 0, OPT_ZMAP}, /* Create .map file */
|
|---|
| 181 | {"Zno-demangle", 0, 0, OPT_ZNODEMANGLE}, /* Don't demangle symbols */
|
|---|
| 182 | {"Zdemangle-proto", 0, 0, OPT_ZDEMANGLEPROTO}, /* Demangle symbols complete */
|
|---|
| 183 | {"Zemx32", 0, 0, OPT_ZEMX32}, /* Create Win32/DOS emx base */
|
|---|
| 184 | {"Zrsx32", 0, 0, OPT_ZRSX32}, /* Create Win32/DOS win32 base */
|
|---|
| 185 | {"Zwin32", 0, 0, OPT_ZWIN32}, /* Create GUI, CUI Win32 */
|
|---|
| 186 | {0, 0, 0, 0}
|
|---|
| 187 | };
|
|---|
| 188 |
|
|---|
| 189 | #include <io.h>
|
|---|
| 190 | #include <fcntl.h>
|
|---|
| 191 | #include <sys/types.h>
|
|---|
| 192 | #include <sys/stat.h>
|
|---|
| 193 | /* bird: clash with abort macro in ld should really include this earlier
|
|---|
| 194 | * Quick fix is to undefine the abort macro.
|
|---|
| 195 | */
|
|---|
| 196 | #undef abort
|
|---|
| 197 | #include <process.h>
|
|---|
| 198 | #define abort() ld_abort (__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
|---|
| 199 | /* bird: include headers for alloca and utime too please */
|
|---|
| 200 | #include <alloca.h>
|
|---|
| 201 | #include <sys/utime.h>
|
|---|
| 202 |
|
|---|
| 203 | static const char *exe_filename;
|
|---|
| 204 | static const char *def_filename = NULL;
|
|---|
| 205 | static const char *res_filename = NULL;
|
|---|
| 206 | static const char *map_filename = NULL;
|
|---|
| 207 | static const char *touch_filename = NULL;
|
|---|
| 208 | static int reloc_flag = 0;
|
|---|
| 209 | static int dll_flag = 0;
|
|---|
| 210 | static int exe_flag = 0;
|
|---|
| 211 | static int map_flag = 0;
|
|---|
| 212 | static int stack_size = 0;
|
|---|
| 213 | static int emxbind_strip = 0;
|
|---|
| 214 | enum exe_bind_type
|
|---|
| 215 | {
|
|---|
| 216 | EMX_DEFAULT, RSXNT_WIN32, RSXNT_RSX, RSXNT_EMX
|
|---|
| 217 | } rsxnt_linked = EMX_DEFAULT;
|
|---|
| 218 |
|
|---|
| 219 | static int gld${EMULATION_NAME}_parse_args (argc, argv)
|
|---|
| 220 | int argc;
|
|---|
| 221 | char **argv;
|
|---|
| 222 | {
|
|---|
| 223 | int longind;
|
|---|
| 224 | int optc;
|
|---|
| 225 | int prevoptind = optind;
|
|---|
| 226 | int prevopterr = opterr;
|
|---|
| 227 |
|
|---|
| 228 | opterr = 0;
|
|---|
| 229 | optc = getopt_long_only (argc, argv, "-", longopts, &longind);
|
|---|
| 230 | opterr = prevopterr;
|
|---|
| 231 |
|
|---|
| 232 | switch (optc)
|
|---|
| 233 | {
|
|---|
| 234 | default:
|
|---|
| 235 | optind = prevoptind;
|
|---|
| 236 | return 0;
|
|---|
| 237 | case OPT_ZEXE:
|
|---|
| 238 | exe_flag = 1;
|
|---|
| 239 | break;
|
|---|
| 240 | case OPT_ZSTACK:
|
|---|
| 241 | stack_size = parse (optarg, "%i", "invalid argument '%s' to -Zstack");
|
|---|
| 242 | break;
|
|---|
| 243 | case OPT_ZMAP:
|
|---|
| 244 | map_flag = 1;
|
|---|
| 245 | map_filename = optarg;
|
|---|
| 246 | break;
|
|---|
| 247 | case OPT_ZNODEMANGLE:
|
|---|
| 248 | fatal ("-Znodemangle not implemented yet");
|
|---|
| 249 | break;
|
|---|
| 250 | case OPT_ZDEMANGLEPROTO:
|
|---|
| 251 | fatal ("-Zdemangle-proto not implemented yet");
|
|---|
| 252 | break;
|
|---|
| 253 | case OPT_ZEMX32:
|
|---|
| 254 | rsxnt_linked = RSXNT_EMX;
|
|---|
| 255 | break;
|
|---|
| 256 | case OPT_ZRSX32:
|
|---|
| 257 | rsxnt_linked = RSXNT_RSX;
|
|---|
| 258 | break;
|
|---|
| 259 | case OPT_ZWIN32:
|
|---|
| 260 | rsxnt_linked = RSXNT_WIN32;
|
|---|
| 261 | break;
|
|---|
| 262 | }
|
|---|
| 263 | return 1;
|
|---|
| 264 | }
|
|---|
| 265 |
|
|---|
| 266 | /*
|
|---|
| 267 | * This routine is used to post-process command-line options,
|
|---|
| 268 | * since after_parse hook is invoked too late for us (changing
|
|---|
| 269 | * output_filename is not effective).
|
|---|
| 270 | */
|
|---|
| 271 | static void gld${EMULATION_NAME}_set_symbols (void)
|
|---|
| 272 | {
|
|---|
| 273 | char *ext, *tmp_dir, *tmp;
|
|---|
| 274 | size_t tmp_dir_len;
|
|---|
| 275 |
|
|---|
| 276 | if (rsxnt_linked != EMX_DEFAULT && link_info.strip != strip_none) /* RSXNT */
|
|---|
| 277 | {
|
|---|
| 278 | /* rsxnt can't live without all (even debugging) symbols??? */
|
|---|
| 279 | link_info.strip = strip_none;
|
|---|
| 280 | emxbind_strip = 1;
|
|---|
| 281 | }
|
|---|
| 282 | else if (link_info.strip != strip_none)
|
|---|
| 283 | {
|
|---|
| 284 | /* emxbind cant live without extern defs... */
|
|---|
| 285 | link_info.strip = strip_debugger;
|
|---|
| 286 | emxbind_strip = 1;
|
|---|
| 287 | }
|
|---|
| 288 |
|
|---|
| 289 | /* Always generate relocatable output since ld is just the first stage ... */
|
|---|
| 290 | link_info.relocateable = TRUE;
|
|---|
| 291 |
|
|---|
| 292 | if (exe_flag)
|
|---|
| 293 | {
|
|---|
| 294 | ext = _getext (output_filename);
|
|---|
| 295 | if ((ext != NULL) && (stricmp (ext, ".exe") == 0))
|
|---|
| 296 | {
|
|---|
| 297 | exe_filename = output_filename;
|
|---|
| 298 | exe_flag = 0;
|
|---|
| 299 | }
|
|---|
| 300 | else
|
|---|
| 301 | {
|
|---|
| 302 | touch_filename = strdup(output_filename);
|
|---|
| 303 | exe_filename = concat (output_filename, ".exe", NULL);
|
|---|
| 304 | }
|
|---|
| 305 | }
|
|---|
| 306 | else
|
|---|
| 307 | {
|
|---|
| 308 | ext = _getext2 (output_filename);
|
|---|
| 309 | if (stricmp (ext, ".dll") == 0)
|
|---|
| 310 | {
|
|---|
| 311 | link_info.relocateable = TRUE;
|
|---|
| 312 | dll_flag = 1;
|
|---|
| 313 | }
|
|---|
| 314 | else if (stricmp (ext, ".exe") != 0)
|
|---|
| 315 | {
|
|---|
| 316 | exe_filename = NULL;
|
|---|
| 317 | return;
|
|---|
| 318 | }
|
|---|
| 319 | exe_filename = output_filename;
|
|---|
| 320 | }
|
|---|
| 321 |
|
|---|
| 322 | /* Create a temporary a.out executable file. */
|
|---|
| 323 |
|
|---|
| 324 | tmp_dir = getenv ("TMPDIR");
|
|---|
| 325 | if (tmp_dir == NULL) tmp_dir = getenv ("TMP");
|
|---|
| 326 | if (tmp_dir == NULL) tmp_dir = getenv ("TEMP");
|
|---|
| 327 | if (tmp_dir == NULL) tmp_dir = ".";
|
|---|
| 328 | tmp_dir_len = strlen (tmp_dir);
|
|---|
| 329 | output_filename = tmp = xmalloc (tmp_dir_len + 10);
|
|---|
| 330 | memcpy (tmp, tmp_dir, tmp_dir_len);
|
|---|
| 331 | if (tmp_dir_len != 0 && strchr ("\\\\/:", tmp_dir[tmp_dir_len-1]) == NULL)
|
|---|
| 332 | tmp[tmp_dir_len++] = '\\\\';
|
|---|
| 333 | strcpy (tmp + tmp_dir_len, "ldXXXXXX");
|
|---|
| 334 | if (mktemp (tmp) == NULL)
|
|---|
| 335 | fatal ("mktemp(\\"%s\\") failed", output_filename);
|
|---|
| 336 |
|
|---|
| 337 | unlink (exe_filename);
|
|---|
| 338 | if (touch_filename != NULL)
|
|---|
| 339 | unlink (touch_filename);
|
|---|
| 340 | }
|
|---|
| 341 |
|
|---|
| 342 | static bfd_boolean gld${EMULATION_NAME}_unrecognized_file (entry)
|
|---|
| 343 | lang_input_statement_type *entry;
|
|---|
| 344 | {
|
|---|
| 345 | char *ext;
|
|---|
| 346 |
|
|---|
| 347 | ext = _getext (entry->filename);
|
|---|
| 348 | if (ext != NULL)
|
|---|
| 349 | {
|
|---|
| 350 | if (stricmp (ext, ".def") == 0)
|
|---|
| 351 | {
|
|---|
| 352 | def_filename = entry->filename;
|
|---|
| 353 | entry->loaded = TRUE;
|
|---|
| 354 | return TRUE;
|
|---|
| 355 | }
|
|---|
| 356 | else if (stricmp (ext, ".res") == 0)
|
|---|
| 357 | {
|
|---|
| 358 | res_filename = entry->filename;
|
|---|
| 359 | entry->loaded = TRUE;
|
|---|
| 360 | return TRUE;
|
|---|
| 361 | }
|
|---|
| 362 | }
|
|---|
| 363 |
|
|---|
| 364 | return FALSE;
|
|---|
| 365 | }
|
|---|
| 366 |
|
|---|
| 367 | extern u_int _System DosCopy (char *pszSource, char *pszTarget, u_int ulOption);
|
|---|
| 368 |
|
|---|
| 369 | /* Perform final action(s) on output file */
|
|---|
| 370 | static void gld${EMULATION_NAME}_finish_link (char *filename)
|
|---|
| 371 | {
|
|---|
| 372 | struct stat statbuf;
|
|---|
| 373 | int filemode, mask;
|
|---|
| 374 |
|
|---|
| 375 | if (stat (output_filename, &statbuf) < 0)
|
|---|
| 376 | fatal ("cannot query file status for %s\\n", output_filename);
|
|---|
| 377 |
|
|---|
| 378 | filemode = statbuf.st_mode;
|
|---|
| 379 |
|
|---|
| 380 | mask = umask (0);
|
|---|
| 381 | umask (mask);
|
|---|
| 382 |
|
|---|
| 383 | if (rsxnt_linked == EMX_DEFAULT && exe_filename)
|
|---|
| 384 | {
|
|---|
| 385 | char *nargv[11];
|
|---|
| 386 | int i, saved_errno;
|
|---|
| 387 |
|
|---|
| 388 | i = 0;
|
|---|
| 389 | nargv[i++] = "emxbind";
|
|---|
| 390 | nargv[i++] = "-bq";
|
|---|
| 391 | if (emxbind_strip)
|
|---|
| 392 | nargv[i++] = "-s";
|
|---|
| 393 | if (def_filename)
|
|---|
| 394 | {
|
|---|
| 395 | nargv[i] = alloca (strlen (def_filename) + 3);
|
|---|
| 396 | strcpy (nargv[i], "-d");
|
|---|
| 397 | strcat (nargv[i], def_filename);
|
|---|
| 398 | i++;
|
|---|
| 399 | }
|
|---|
| 400 | else if (dll_flag)
|
|---|
| 401 | nargv[i++] = "-d";
|
|---|
| 402 |
|
|---|
| 403 | if (stack_size != 0)
|
|---|
| 404 | {
|
|---|
| 405 | nargv[i] = alloca (20);
|
|---|
| 406 | sprintf (nargv[i], "-k0x%x", stack_size);
|
|---|
| 407 | i++;
|
|---|
| 408 | }
|
|---|
| 409 |
|
|---|
| 410 | if (map_flag)
|
|---|
| 411 | {
|
|---|
| 412 | if (map_filename == NULL)
|
|---|
| 413 | {
|
|---|
| 414 | map_filename = alloca (strlen (exe_filename) + 5);
|
|---|
| 415 | strcpy ((char *)map_filename, exe_filename);
|
|---|
| 416 | _remext ((char *)map_filename);
|
|---|
| 417 | strcat ((char *)map_filename, ".map");
|
|---|
| 418 | }
|
|---|
| 419 | nargv[i] = alloca (strlen (map_filename) + 3);
|
|---|
| 420 | strcpy (nargv[i], "-m");
|
|---|
| 421 | strcat (nargv[i], map_filename);
|
|---|
| 422 | i++;
|
|---|
| 423 | }
|
|---|
| 424 |
|
|---|
| 425 | if (res_filename)
|
|---|
| 426 | {
|
|---|
| 427 | nargv[i] = alloca (strlen (res_filename) + 3);
|
|---|
| 428 | strcpy (nargv[i], "-r");
|
|---|
| 429 | strcat (nargv[i], res_filename);
|
|---|
| 430 | i++;
|
|---|
| 431 | }
|
|---|
| 432 |
|
|---|
| 433 | nargv[i++] = "-o";
|
|---|
| 434 | nargv[i++] = (char *)exe_filename;
|
|---|
| 435 | nargv[i++] = (char *)output_filename;
|
|---|
| 436 | nargv[i] = NULL;
|
|---|
| 437 | i = spawnvp (P_WAIT, "emxbind", nargv);
|
|---|
| 438 | saved_errno = errno; unlink (output_filename); errno = saved_errno;
|
|---|
| 439 | if (i < 0)
|
|---|
| 440 | fatal ("failed to run emxbind\\n", NULL);
|
|---|
| 441 | else if (i != 0)
|
|---|
| 442 | fatal ("emxbind failed\\n", NULL);
|
|---|
| 443 |
|
|---|
| 444 | if (chmod (exe_filename, filemode | (0111 & ~mask)) == -1)
|
|---|
| 445 | fatal ("failed to write file %s\\n", exe_filename);
|
|---|
| 446 |
|
|---|
| 447 | if (touch_filename)
|
|---|
| 448 | {
|
|---|
| 449 | char execname[512];
|
|---|
| 450 | _execname(execname, sizeof(execname));
|
|---|
| 451 | strcpy(_getname(execname), "ldstub.bin");
|
|---|
| 452 | /* Copy stub into file */
|
|---|
| 453 | if (DosCopy(execname, (char *)touch_filename, 4))
|
|---|
| 454 | fatal ("cannot copy %s to %s\\n", execname, touch_filename);
|
|---|
| 455 | /* Now touch it */
|
|---|
| 456 | if (utime (touch_filename, NULL))
|
|---|
| 457 | fatal ("cannot touch file %s\\n", touch_filename);
|
|---|
| 458 | }
|
|---|
| 459 | }
|
|---|
| 460 | else if (exe_filename) /* RSXNT */
|
|---|
| 461 | {
|
|---|
| 462 | char *nargv[10];
|
|---|
| 463 | int i, saved_errno;
|
|---|
| 464 |
|
|---|
| 465 | i = 0;
|
|---|
| 466 | nargv[i++] = "ntbind";
|
|---|
| 467 | if (emxbind_strip)
|
|---|
| 468 | nargv[i++] = "-s";
|
|---|
| 469 | nargv[i++] = "-o";
|
|---|
| 470 | nargv[i++] = (char *)exe_filename;
|
|---|
| 471 | nargv[i++] = (char *)output_filename;
|
|---|
| 472 |
|
|---|
| 473 | if (rsxnt_linked == RSXNT_WIN32)
|
|---|
| 474 | nargv[i++] = (emxbind_strip) ? "dosstub.dos" : "dosstub.dbg";
|
|---|
| 475 | else
|
|---|
| 476 | {
|
|---|
| 477 | nargv[i++] = "dosstub.rsx";
|
|---|
| 478 | if (emxbind_strip)
|
|---|
| 479 | nargv[i++] = "-strip";
|
|---|
| 480 | }
|
|---|
| 481 |
|
|---|
| 482 | if (def_filename)
|
|---|
| 483 | {
|
|---|
| 484 | nargv[i++] = "-d";
|
|---|
| 485 | nargv[i] = alloca (strlen (def_filename) + 3);
|
|---|
| 486 | strcpy(nargv[i], def_filename);
|
|---|
| 487 | i++;
|
|---|
| 488 | }
|
|---|
| 489 | nargv[i] = NULL;
|
|---|
| 490 |
|
|---|
| 491 | i = spawnvp (P_WAIT, "ntbind", nargv);
|
|---|
| 492 | saved_errno = errno; unlink (output_filename); errno = saved_errno;
|
|---|
| 493 | if (i < 0)
|
|---|
| 494 | fatal ("failed to run ntbind\\n", NULL);
|
|---|
| 495 | else if (i != 0)
|
|---|
| 496 | fatal ("ntbind failed\\n", NULL);
|
|---|
| 497 |
|
|---|
| 498 | if (chmod (exe_filename, filemode | (0111 & ~mask)) == -1)
|
|---|
| 499 | fatal ("failed to write file %s\\n", exe_filename);
|
|---|
| 500 |
|
|---|
| 501 | if (touch_filename)
|
|---|
| 502 | {
|
|---|
| 503 | i = open (touch_filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
|
|---|
| 504 | if (i < 0)
|
|---|
| 505 | fatal ("failed to touch file %s\\n", touch_filename);
|
|---|
| 506 | close (i);
|
|---|
| 507 | }
|
|---|
| 508 | }
|
|---|
| 509 | }
|
|---|
| 510 |
|
|---|
| 511 | /* Create any output sections needed by the target. */
|
|---|
| 512 | static void gld${EMULATION_NAME}_create_output_section_statements (void)
|
|---|
| 513 | {
|
|---|
| 514 | /* Since we enabled relocations LD marked output file as non-pageable */
|
|---|
| 515 | /* However, this is not TRUE for emx: always generate paged output */
|
|---|
| 516 | output_bfd->flags |= D_PAGED;
|
|---|
| 517 | }
|
|---|
| 518 |
|
|---|
| 519 | struct ld_emulation_xfer_struct ld_${EMULATION_NAME}_emulation =
|
|---|
| 520 | {
|
|---|
| 521 | gld${EMULATION_NAME}_before_parse,
|
|---|
| 522 | syslib_default,
|
|---|
| 523 | hll_default,
|
|---|
| 524 | after_parse_default,
|
|---|
| 525 | after_open_default,
|
|---|
| 526 | after_allocation_default,
|
|---|
| 527 | set_output_arch_default,
|
|---|
| 528 | ldemul_default_target,
|
|---|
| 529 | before_allocation_default,
|
|---|
| 530 | gld${EMULATION_NAME}_get_script,
|
|---|
| 531 | "${EMULATION_NAME}",
|
|---|
| 532 | "${OUTPUT_FORMAT}",
|
|---|
| 533 | NULL, /* finish */
|
|---|
| 534 | gld${EMULATION_NAME}_create_output_section_statements, /* create output section statements */
|
|---|
| 535 | NULL, /* open dynamic archive */
|
|---|
| 536 | NULL, /* place orphan */
|
|---|
| 537 | gld${EMULATION_NAME}_set_symbols, /* set symbols */
|
|---|
| 538 | gld${EMULATION_NAME}_parse_args,
|
|---|
| 539 | NULL, /* add_options */
|
|---|
| 540 | NULL, /* handle_option */
|
|---|
| 541 | gld${EMULATION_NAME}_unrecognized_file,
|
|---|
| 542 | NULL, /* list_options */
|
|---|
| 543 | NULL, /* recognized_file */
|
|---|
| 544 | NULL, /* find_potential_libraries */
|
|---|
| 545 | NULL, /* new_vers_pattern. */
|
|---|
| 546 | gld${EMULATION_NAME}_finish_link
|
|---|
| 547 | };
|
|---|
| 548 | EOF
|
|---|