arc: Add support for ARC HS extra registers in core files
[deliverable/binutils-gdb.git] / bfd / vms-alpha.c
CommitLineData
95e34ef7 1/* vms.c -- BFD back-end for EVAX (openVMS/Alpha) files.
b3adc24a 2 Copyright (C) 1996-2020 Free Software Foundation, Inc.
95e34ef7
TG
3
4 Initial version written by Klaus Kaempf (kkaempf@rmi.de)
5 Major rewrite by Adacore.
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
9 the Free Software Foundation; either version 3 of the License, or
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
19 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
21
22/* TODO:
f9eeb9c9 23 o overlayed sections
95e34ef7
TG
24 o PIC
25 o Generation of shared image
95e34ef7
TG
26 o Relocation optimizations
27 o EISD for the stack
28 o Vectors isect
29 o 64 bits sections
30 o Entry point
f9eeb9c9
TG
31 o LIB$INITIALIZE
32 o protected sections (for messages)
95e34ef7
TG
33 ...
34*/
35
36#include "sysdep.h"
37#include "bfd.h"
38#include "bfdlink.h"
39#include "libbfd.h"
40#include "bfdver.h"
41
42#include "vms.h"
43#include "vms/eihd.h"
44#include "vms/eiha.h"
45#include "vms/eihi.h"
46#include "vms/eihs.h"
47#include "vms/eisd.h"
48#include "vms/dmt.h"
49#include "vms/dst.h"
50#include "vms/eihvn.h"
51#include "vms/eobjrec.h"
52#include "vms/egsd.h"
53#include "vms/egps.h"
9a1b4480 54#include "vms/esgps.h"
95e34ef7
TG
55#include "vms/eeom.h"
56#include "vms/emh.h"
57#include "vms/eiaf.h"
58#include "vms/shl.h"
59#include "vms/eicp.h"
60#include "vms/etir.h"
61#include "vms/egsy.h"
62#include "vms/esdf.h"
63#include "vms/esdfm.h"
64#include "vms/esdfv.h"
65#include "vms/esrf.h"
66#include "vms/egst.h"
9a1b4480 67#include "vms/eidc.h"
95e34ef7
TG
68#include "vms/dsc.h"
69#include "vms/prt.h"
70#include "vms/internal.h"
71\f
72
73#define MIN(a,b) ((a) < (b) ? (a) : (b))
74
75/* The r_type field in a reloc is one of the following values. */
76#define ALPHA_R_IGNORE 0
77#define ALPHA_R_REFQUAD 1
78#define ALPHA_R_BRADDR 2
79#define ALPHA_R_HINT 3
80#define ALPHA_R_SREL16 4
81#define ALPHA_R_SREL32 5
82#define ALPHA_R_SREL64 6
83#define ALPHA_R_OP_PUSH 7
84#define ALPHA_R_OP_STORE 8
85#define ALPHA_R_OP_PSUB 9
86#define ALPHA_R_OP_PRSHIFT 10
87#define ALPHA_R_LINKAGE 11
88#define ALPHA_R_REFLONG 12
89#define ALPHA_R_CODEADDR 13
90#define ALPHA_R_NOP 14
91#define ALPHA_R_BSR 15
92#define ALPHA_R_LDA 16
93#define ALPHA_R_BOH 17
44273c5b 94
95e34ef7
TG
95/* These are used with DST_S_C_LINE_NUM. */
96#define DST_S_C_LINE_NUM_HEADER_SIZE 4
97
98/* These are used with DST_S_C_SOURCE */
99
100#define DST_S_B_PCLINE_UNSBYTE 1
101#define DST_S_W_PCLINE_UNSWORD 1
102#define DST_S_L_PCLINE_UNSLONG 1
103
104#define DST_S_B_MODBEG_NAME 14
105#define DST_S_L_RTNBEG_ADDRESS 5
106#define DST_S_B_RTNBEG_NAME 13
107#define DST_S_L_RTNEND_SIZE 5
108
109/* These are used with DST_S_C_SOURCE. */
110#define DST_S_C_SOURCE_HEADER_SIZE 4
111
112#define DST_S_B_SRC_DF_LENGTH 1
113#define DST_S_W_SRC_DF_FILEID 3
114#define DST_S_B_SRC_DF_FILENAME 20
115#define DST_S_B_SRC_UNSBYTE 1
116#define DST_S_W_SRC_UNSWORD 1
117#define DST_S_L_SRC_UNSLONG 1
118
119/* Debugger symbol definitions. */
120
07d6d2b8
AM
121#define DBG_S_L_DMT_MODBEG 0
122#define DBG_S_L_DST_SIZE 4
123#define DBG_S_W_DMT_PSECT_COUNT 8
95e34ef7
TG
124#define DBG_S_C_DMT_HEADER_SIZE 12
125
07d6d2b8 126#define DBG_S_L_DMT_PSECT_START 0
95e34ef7 127#define DBG_S_L_DMT_PSECT_LENGTH 4
07d6d2b8 128#define DBG_S_C_DMT_PSECT_SIZE 8
95e34ef7
TG
129
130/* VMS module header. */
131
132struct hdr_struct
133{
134 char hdr_b_strlvl;
135 int hdr_l_arch1;
136 int hdr_l_arch2;
137 int hdr_l_recsiz;
138 char *hdr_t_name;
139 char *hdr_t_version;
140 char *hdr_t_date;
141 char *hdr_c_lnm;
142 char *hdr_c_src;
143 char *hdr_c_ttl;
144};
145
146#define EMH_DATE_LENGTH 17
147
148/* VMS End-Of-Module records (EOM/EEOM). */
149
150struct eom_struct
151{
152 unsigned int eom_l_total_lps;
153 unsigned short eom_w_comcod;
154 bfd_boolean eom_has_transfer;
155 unsigned char eom_b_tfrflg;
156 unsigned int eom_l_psindx;
157 unsigned int eom_l_tfradr;
158};
159
160struct vms_symbol_entry
161{
162 bfd *owner;
163
164 /* Common fields. */
165 unsigned char typ;
166 unsigned char data_type;
167 unsigned short flags;
168
169 /* Section and offset/value of the symbol. */
95e34ef7 170 unsigned int value;
a928f1d7 171 asection *section;
95e34ef7
TG
172
173 /* Section and offset/value for the entry point (only for subprg). */
a928f1d7 174 asection *code_section;
95e34ef7
TG
175 unsigned int code_value;
176
177 /* Symbol vector offset. */
178 unsigned int symbol_vector;
179
180 /* Length of the name. */
181 unsigned char namelen;
182
183 char name[1];
184};
185
186/* Stack value for push/pop commands. */
187
188struct stack_struct
189{
190 bfd_vma value;
191 unsigned int reloc;
192};
193
194#define STACKSIZE 128
195
196/* A minimal decoding of DST compilation units. We only decode
197 what's needed to get to the line number information. */
198
199struct fileinfo
200{
201 char *name;
202 unsigned int srec;
203};
204
205struct srecinfo
206{
207 struct srecinfo *next;
208 unsigned int line;
209 unsigned int sfile;
210 unsigned int srec;
211};
212
213struct lineinfo
214{
215 struct lineinfo *next;
216 bfd_vma address;
217 unsigned int line;
218};
219
220struct funcinfo
221{
222 struct funcinfo *next;
223 char *name;
224 bfd_vma low;
225 bfd_vma high;
226};
227
228struct module
229{
230 /* Chain the previously read compilation unit. */
231 struct module *next;
232
233 /* The module name. */
234 char *name;
235
236 /* The start offset and size of debug info in the DST section. */
237 unsigned int modbeg;
238 unsigned int size;
239
240 /* The lowest and highest addresses contained in this compilation
241 unit as specified in the compilation unit header. */
242 bfd_vma low;
243 bfd_vma high;
244
245 /* The listing line table. */
246 struct lineinfo *line_table;
247
248 /* The source record table. */
249 struct srecinfo *srec_table;
250
251 /* A list of the functions found in this module. */
252 struct funcinfo *func_table;
253
254 /* Current allocation of file_table. */
255 unsigned int file_table_count;
256
257 /* An array of the files making up this module. */
258 struct fileinfo *file_table;
259};
260
261/* BFD private data for alpha-vms. */
262
263struct vms_private_data_struct
264{
265 /* If true, relocs have been read. */
266 bfd_boolean reloc_done;
267
268 /* Record input buffer. */
269 struct vms_rec_rd recrd;
270 struct vms_rec_wr recwr;
271
272 struct hdr_struct hdr_data; /* data from HDR/EMH record */
273 struct eom_struct eom_data; /* data from EOM/EEOM record */
c734eb83 274
46d00b8a
TG
275 /* Transfer addresses (entry points). */
276 bfd_vma transfer_address[4];
277
c734eb83 278 /* Array of GSD sections to get the correspond BFD one. */
07d6d2b8 279 unsigned int section_max; /* Size of the sections array. */
c734eb83
TG
280 unsigned int section_count; /* Number of GSD sections. */
281 asection **sections;
95e34ef7
TG
282
283 /* Array of raw symbols. */
284 struct vms_symbol_entry **syms;
285
286 /* Canonicalized symbols. */
287 asymbol **csymbols;
288
289 /* Number of symbols. */
290 unsigned int gsd_sym_count;
291 /* Size of the syms array. */
292 unsigned int max_sym_count;
293 /* Number of procedure symbols. */
294 unsigned int norm_sym_count;
295
296 /* Stack used to evaluate TIR/ETIR commands. */
297 struct stack_struct *stack;
298 int stackptr;
299
300 /* Content reading. */
301 asection *image_section; /* section for image_ptr */
302 file_ptr image_offset; /* Offset for image_ptr. */
95e34ef7
TG
303
304 struct module *modules; /* list of all compilation units */
305
8185f55c 306 /* The DST section. */
95e34ef7
TG
307 asection *dst_section;
308
309 unsigned int dst_ptr_offsets_count; /* # of offsets in following array */
310 unsigned int *dst_ptr_offsets; /* array of saved image_ptr offsets */
311
312 /* Shared library support */
313 bfd_vma symvva; /* relative virtual address of symbol vector */
314 unsigned int ident;
315 unsigned char matchctl;
316
317 /* Shared library index. This is used for input bfd while linking. */
318 unsigned int shr_index;
319
320 /* Used to place structures in the file. */
321 file_ptr file_pos;
322
323 /* Simply linked list of eisd. */
324 struct vms_internal_eisd_map *eisd_head;
325 struct vms_internal_eisd_map *eisd_tail;
326
327 /* Simply linked list of eisd for shared libraries. */
328 struct vms_internal_eisd_map *gbl_eisd_head;
329 struct vms_internal_eisd_map *gbl_eisd_tail;
330
331 /* linkage index counter used by conditional store commands */
25d41743 332 unsigned int vms_linkage_index;
95e34ef7
TG
333};
334
335#define PRIV2(abfd, name) \
336 (((struct vms_private_data_struct *)(abfd)->tdata.any)->name)
337#define PRIV(name) PRIV2(abfd,name)
338
339
340/* Used to keep extra VMS specific information for a given section.
341
342 reloc_size holds the size of the relocation stream, note this
343 is very different from the number of relocations as VMS relocations
344 are variable length.
345
346 reloc_stream is the actual stream of relocation entries. */
347
348struct vms_section_data_struct
349{
350 /* Maximnum number of entries in sec->relocation. */
351 unsigned reloc_max;
352
353 /* Corresponding eisd. Used only while generating executables. */
354 struct vms_internal_eisd_map *eisd;
355
356 /* PSC flags to be clear. */
357 flagword no_flags;
358
359 /* PSC flags to be set. */
360 flagword flags;
361};
362
363#define vms_section_data(sec) \
364 ((struct vms_section_data_struct *)sec->used_by_bfd)
365
366/* To be called from the debugger. */
0a9d414a 367struct vms_private_data_struct *bfd_vms_get_data (bfd *);
95e34ef7 368
0a9d414a 369static int vms_get_remaining_object_record (bfd *, unsigned int);
95e34ef7 370static bfd_boolean _bfd_vms_slurp_object_records (bfd * abfd);
96d3b80f
AM
371static bfd_boolean alpha_vms_add_fixup_lp (struct bfd_link_info *,
372 bfd *, bfd *);
373static bfd_boolean alpha_vms_add_fixup_ca (struct bfd_link_info *,
374 bfd *, bfd *);
375static bfd_boolean alpha_vms_add_fixup_qr (struct bfd_link_info *,
376 bfd *, bfd *, bfd_vma);
377static bfd_boolean alpha_vms_add_fixup_lr (struct bfd_link_info *,
378 unsigned int, bfd_vma);
379static bfd_boolean alpha_vms_add_lw_reloc (struct bfd_link_info *);
380static bfd_boolean alpha_vms_add_qw_reloc (struct bfd_link_info *);
95e34ef7
TG
381
382struct vector_type
383{
384 unsigned int max_el;
385 unsigned int nbr_el;
386 void *els;
387};
388
389/* Number of elements in VEC. */
390
391#define VEC_COUNT(VEC) ((VEC).nbr_el)
392
393/* Get the address of the Nth element. */
394
395#define VEC_EL(VEC, TYPE, N) (((TYPE *)((VEC).els))[N])
396
07d6d2b8
AM
397#define VEC_INIT(VEC) \
398 do { \
399 (VEC).max_el = 0; \
400 (VEC).nbr_el = 0; \
401 (VEC).els = NULL; \
95e34ef7
TG
402 } while (0)
403
404/* Be sure there is room for a new element. */
405
96d3b80f 406static void *vector_grow1 (struct vector_type *vec, size_t elsz);
95e34ef7
TG
407
408/* Allocate room for a new element and return its address. */
409
07d6d2b8 410#define VEC_APPEND(VEC, TYPE) \
96d3b80f 411 ((TYPE *) vector_grow1 (&VEC, sizeof (TYPE)))
95e34ef7
TG
412
413struct alpha_vms_vma_ref
414{
415 bfd_vma vma; /* Vma in the output. */
416 bfd_vma ref; /* Reference in the input. */
417};
418
419struct alpha_vms_shlib_el
420{
421 bfd *abfd;
422 bfd_boolean has_fixups;
423
424 struct vector_type lp; /* Vector of bfd_vma. */
425 struct vector_type ca; /* Vector of bfd_vma. */
426 struct vector_type qr; /* Vector of struct alpha_vms_vma_ref. */
427};
428
429/* Alpha VMS linker hash table. */
430
431struct alpha_vms_link_hash_table
432{
433 struct bfd_link_hash_table root;
434
cc643b88 435 /* Vector of shared libraries. */
95e34ef7
TG
436 struct vector_type shrlibs;
437
438 /* Fixup section. */
439 asection *fixup;
440
441 /* Base address. Used by fixups. */
442 bfd_vma base_addr;
443};
444
445#define alpha_vms_link_hash(INFO) \
446 ((struct alpha_vms_link_hash_table *)(INFO->hash))
447
448/* Alpha VMS linker hash table entry. */
449
450struct alpha_vms_link_hash_entry
451{
452 struct bfd_link_hash_entry root;
453
454 /* Pointer to the original vms symbol. */
455 struct vms_symbol_entry *sym;
456};
457\f
458/* Image reading. */
459
460/* Read & process EIHD record.
461 Return TRUE on success, FALSE on error. */
462
463static bfd_boolean
464_bfd_vms_slurp_eihd (bfd *abfd, unsigned int *eisd_offset,
07d6d2b8 465 unsigned int *eihs_offset)
95e34ef7
TG
466{
467 unsigned int imgtype, size;
468 bfd_vma symvva;
469 struct vms_eihd *eihd = (struct vms_eihd *)PRIV (recrd.rec);
470
471 vms_debug2 ((8, "_bfd_vms_slurp_eihd\n"));
472
ca4cf9b9
NC
473 /* PR 21813: Check for an undersized record. */
474 if (PRIV (recrd.buf_size) < sizeof (* eihd))
475 {
38f14ab8 476 _bfd_error_handler (_("corrupt EIHD record - size is too small"));
ca4cf9b9
NC
477 bfd_set_error (bfd_error_bad_value);
478 return FALSE;
479 }
480
95e34ef7
TG
481 size = bfd_getl32 (eihd->size);
482 imgtype = bfd_getl32 (eihd->imgtype);
483
484 if (imgtype == EIHD__K_EXE || imgtype == EIHD__K_LIM)
485 abfd->flags |= EXEC_P;
486
487 symvva = bfd_getl64 (eihd->symvva);
488 if (symvva != 0)
489 {
490 PRIV (symvva) = symvva;
491 abfd->flags |= DYNAMIC;
492 }
493
494 PRIV (ident) = bfd_getl32 (eihd->ident);
495 PRIV (matchctl) = eihd->matchctl;
496
497 *eisd_offset = bfd_getl32 (eihd->isdoff);
498 *eihs_offset = bfd_getl32 (eihd->symdbgoff);
499
500 vms_debug2 ((4, "EIHD size %d imgtype %d symvva 0x%lx eisd %d eihs %d\n",
07d6d2b8
AM
501 size, imgtype, (unsigned long)symvva,
502 *eisd_offset, *eihs_offset));
8ab484c2 503 (void) size;
95e34ef7 504
ddfb684a 505 return TRUE;
95e34ef7
TG
506}
507
508/* Read & process EISD record.
509 Return TRUE on success, FALSE on error. */
510
511static bfd_boolean
512_bfd_vms_slurp_eisd (bfd *abfd, unsigned int offset)
513{
514 int section_count = 0;
515
516 vms_debug2 ((8, "_bfd_vms_slurp_eisd\n"));
517
518 while (1)
519 {
520 struct vms_eisd *eisd;
521 unsigned int rec_size;
522 unsigned int size;
ce9116fd 523 bfd_uint64_t vaddr;
95e34ef7
TG
524 unsigned int flags;
525 unsigned int vbn;
526 char *name = NULL;
527 asection *section;
528 flagword bfd_flags;
529
bf31e604
AM
530 /* PR 17512: file: 3d9e9fe9. */
531 if (offset > PRIV (recrd.rec_size)
532 || (PRIV (recrd.rec_size) - offset
533 < offsetof (struct vms_eisd, eisdsize) + 4))
5860e3f8 534 return FALSE;
bf31e604 535 eisd = (struct vms_eisd *) (PRIV (recrd.rec) + offset);
95e34ef7 536 rec_size = bfd_getl32 (eisd->eisdsize);
95e34ef7 537 if (rec_size == 0)
07d6d2b8 538 break;
95e34ef7
TG
539
540 /* Skip to next block if pad. */
541 if (rec_size == 0xffffffff)
07d6d2b8
AM
542 {
543 offset = (offset + VMS_BLOCK_SIZE) & ~(VMS_BLOCK_SIZE - 1);
544 continue;
545 }
7adc0a81
NC
546
547 /* Make sure that there is enough data present in the record. */
bf31e604 548 if (rec_size < offsetof (struct vms_eisd, type) + 1)
7adc0a81
NC
549 return FALSE;
550 /* Make sure that the record is not too big either. */
bf31e604 551 if (rec_size > PRIV (recrd.rec_size) - offset)
7adc0a81
NC
552 return FALSE;
553
554 offset += rec_size;
95e34ef7
TG
555
556 size = bfd_getl32 (eisd->secsize);
557 vaddr = bfd_getl64 (eisd->virt_addr);
558 flags = bfd_getl32 (eisd->flags);
559 vbn = bfd_getl32 (eisd->vbn);
560
561 vms_debug2 ((4, "EISD at 0x%x size 0x%x addr 0x%lx flags 0x%x blk %d\n",
07d6d2b8 562 offset, size, (unsigned long)vaddr, flags, vbn));
95e34ef7
TG
563
564 /* VMS combines psects from .obj files into isects in the .exe. This
565 process doesn't preserve enough information to reliably determine
566 what's in each section without examining the data. This is
567 especially true of DWARF debug sections. */
568 bfd_flags = SEC_ALLOC;
c068d5be 569 if (vbn != 0)
07d6d2b8 570 bfd_flags |= SEC_HAS_CONTENTS | SEC_LOAD;
95e34ef7
TG
571
572 if (flags & EISD__M_EXE)
c068d5be 573 bfd_flags |= SEC_CODE;
95e34ef7
TG
574
575 if (flags & EISD__M_NONSHRADR)
c068d5be 576 bfd_flags |= SEC_DATA;
95e34ef7
TG
577
578 if (!(flags & EISD__M_WRT))
579 bfd_flags |= SEC_READONLY;
580
581 if (flags & EISD__M_DZRO)
582 bfd_flags |= SEC_DATA;
583
584 if (flags & EISD__M_FIXUPVEC)
c068d5be 585 bfd_flags |= SEC_DATA;
95e34ef7
TG
586
587 if (flags & EISD__M_CRF)
c068d5be 588 bfd_flags |= SEC_DATA;
95e34ef7
TG
589
590 if (flags & EISD__M_GBL)
591 {
bf31e604 592 if (rec_size <= offsetof (struct vms_eisd, gblnam))
7adc0a81
NC
593 return FALSE;
594 else if (rec_size < sizeof (struct vms_eisd))
37d2e9c7 595 name = _bfd_vms_save_counted_string (abfd, eisd->gblnam,
7adc0a81
NC
596 rec_size - offsetof (struct vms_eisd, gblnam));
597 else
37d2e9c7
AM
598 name = _bfd_vms_save_counted_string (abfd, eisd->gblnam,
599 EISD__K_GBLNAMLEN);
bf31e604 600 if (name == NULL || name[0] == 0)
37d2e9c7 601 return FALSE;
95e34ef7
TG
602 bfd_flags |= SEC_COFF_SHARED_LIBRARY;
603 bfd_flags &= ~(SEC_ALLOC | SEC_LOAD);
604 }
605 else if (flags & EISD__M_FIXUPVEC)
07d6d2b8 606 name = "$FIXUPVEC$";
95e34ef7 607 else if (eisd->type == EISD__K_USRSTACK)
07d6d2b8 608 name = "$STACK$";
95e34ef7
TG
609 else
610 {
07d6d2b8 611 const char *pfx;
95e34ef7 612
37d2e9c7
AM
613 name = (char *) bfd_alloc (abfd, 32);
614 if (name == NULL)
615 return FALSE;
07d6d2b8
AM
616 if (flags & EISD__M_DZRO)
617 pfx = "BSS";
618 else if (flags & EISD__M_EXE)
619 pfx = "CODE";
620 else if (!(flags & EISD__M_WRT))
621 pfx = "RO";
622 else
623 pfx = "LOCAL";
624 BFD_ASSERT (section_count < 999);
95e34ef7
TG
625 sprintf (name, "$%s_%03d$", pfx, section_count++);
626 }
627
628 section = bfd_make_section (abfd, name);
629
630 if (!section)
631 return FALSE;
632
633 section->filepos = vbn ? VMS_BLOCK_SIZE * (vbn - 1) : 0;
634 section->size = size;
635 section->vma = vaddr;
636
fd361982 637 if (!bfd_set_section_flags (section, bfd_flags))
95e34ef7
TG
638 return FALSE;
639 }
640
641 return TRUE;
642}
643
644/* Read & process EIHS record.
645 Return TRUE on success, FALSE on error. */
646
647static bfd_boolean
648_bfd_vms_slurp_eihs (bfd *abfd, unsigned int offset)
649{
650 unsigned char *p = PRIV (recrd.rec) + offset;
80053e46
NC
651 unsigned int gstvbn;
652 unsigned int gstsize ATTRIBUTE_UNUSED;
653 unsigned int dstvbn;
654 unsigned int dstsize;
655 unsigned int dmtvbn;
656 unsigned int dmtbytes;
95e34ef7
TG
657 asection *section;
658
80053e46
NC
659 /* PR 21611: Check that offset is valid. */
660 if (offset > PRIV (recrd.rec_size) - (EIHS__L_DMTBYTES + 4))
661 {
38f14ab8
AM
662 _bfd_error_handler (_("unable to read EIHS record at offset %#x"),
663 offset);
80053e46
NC
664 bfd_set_error (bfd_error_file_truncated);
665 return FALSE;
666 }
667
668 gstvbn = bfd_getl32 (p + EIHS__L_GSTVBN);
669 gstsize = bfd_getl32 (p + EIHS__L_GSTSIZE);
670 dstvbn = bfd_getl32 (p + EIHS__L_DSTVBN);
671 dstsize = bfd_getl32 (p + EIHS__L_DSTSIZE);
672 dmtvbn = bfd_getl32 (p + EIHS__L_DMTVBN);
673 dmtbytes = bfd_getl32 (p + EIHS__L_DMTBYTES);
674
95e34ef7
TG
675#if VMS_DEBUG
676 vms_debug (8, "_bfd_vms_slurp_ihs\n");
677 vms_debug (4, "EIHS record gstvbn %d gstsize %d dstvbn %d dstsize %d dmtvbn %d dmtbytes %d\n",
678 gstvbn, gstsize, dstvbn, dstsize, dmtvbn, dmtbytes);
679#endif
680
681 if (dstvbn)
682 {
683 flagword bfd_flags = SEC_HAS_CONTENTS | SEC_DEBUGGING;
684
685 section = bfd_make_section (abfd, "$DST$");
686 if (!section)
687 return FALSE;
688
689 section->size = dstsize;
690 section->filepos = VMS_BLOCK_SIZE * (dstvbn - 1);
691
fd361982 692 if (!bfd_set_section_flags (section, bfd_flags))
95e34ef7
TG
693 return FALSE;
694
695 PRIV (dst_section) = section;
696 abfd->flags |= (HAS_DEBUG | HAS_LINENO);
697 }
698
699 if (dmtvbn)
700 {
701 flagword bfd_flags = SEC_HAS_CONTENTS | SEC_DEBUGGING;
702
703 section = bfd_make_section (abfd, "$DMT$");
704 if (!section)
705 return FALSE;
706
707 section->size = dmtbytes;
708 section->filepos = VMS_BLOCK_SIZE * (dmtvbn - 1);
709
fd361982 710 if (!bfd_set_section_flags (section, bfd_flags))
95e34ef7
TG
711 return FALSE;
712 }
713
714 if (gstvbn)
715 {
95e34ef7
TG
716 if (bfd_seek (abfd, VMS_BLOCK_SIZE * (gstvbn - 1), SEEK_SET))
717 {
718 bfd_set_error (bfd_error_file_truncated);
719 return FALSE;
720 }
721
535b785f 722 if (!_bfd_vms_slurp_object_records (abfd))
95e34ef7
TG
723 return FALSE;
724
95e34ef7
TG
725 abfd->flags |= HAS_SYMS;
726 }
727
728 return TRUE;
729}
730\f
731/* Object file reading. */
732
733/* Object file input functions. */
734
735/* Get next record from object file to vms_buf.
736 Set PRIV(buf_size) and return it
737
738 This is a little tricky since it should be portable.
739
740 The openVMS object file has 'variable length' which means that
741 read() returns data in chunks of (hopefully) correct and expected
742 size. The linker (and other tools on VMS) depend on that. Unix
743 doesn't know about 'formatted' files, so reading and writing such
744 an object file in a Unix environment is not trivial.
745
746 With the tool 'file' (available on all VMS FTP sites), one
747 can view and change the attributes of a file. Changing from
748 'variable length' to 'fixed length, 512 bytes' reveals the
749 record size at the first 2 bytes of every record. The same
750 may happen during the transfer of object files from VMS to Unix,
751 at least with UCX, the DEC implementation of TCP/IP.
752
753 The VMS format repeats the size at bytes 2 & 3 of every record.
754
755 On the first call (file_format == FF_UNKNOWN) we check if
756 the first and the third byte pair (!) of the record match.
757 If they do it's an object file in an Unix environment or with
758 wrong attributes (FF_FOREIGN), else we should be in a VMS
759 environment where read() returns the record size (FF_NATIVE).
760
761 Reading is always done in 2 steps:
762 1. first just the record header is read and the size extracted,
763 2. then the read buffer is adjusted and the remaining bytes are
764 read in.
765
766 All file I/O is done on even file positions. */
767
768#define VMS_OBJECT_ADJUSTMENT 2
769
770static void
771maybe_adjust_record_pointer_for_object (bfd *abfd)
772{
773 /* Set the file format once for all on the first invocation. */
774 if (PRIV (recrd.file_format) == FF_UNKNOWN)
775 {
776 if (PRIV (recrd.rec)[0] == PRIV (recrd.rec)[4]
777 && PRIV (recrd.rec)[1] == PRIV (recrd.rec)[5])
778 PRIV (recrd.file_format) = FF_FOREIGN;
779 else
780 PRIV (recrd.file_format) = FF_NATIVE;
781 }
782
783 /* The adjustment is needed only in an Unix environment. */
784 if (PRIV (recrd.file_format) == FF_FOREIGN)
785 PRIV (recrd.rec) += VMS_OBJECT_ADJUSTMENT;
786}
787
788/* Implement step #1 of the object record reading procedure.
789 Return the record type or -1 on failure. */
790
791static int
792_bfd_vms_get_object_record (bfd *abfd)
793{
ddfb684a 794 unsigned int test_len = 6;
95e34ef7 795 int type;
95e34ef7
TG
796
797 vms_debug2 ((8, "_bfd_vms_get_obj_record\n"));
798
ddfb684a 799 /* Skip alignment byte if the current position is odd. */
af47dcbf 800 if (PRIV (recrd.file_format) == FF_FOREIGN && (bfd_tell (abfd) & 1))
95e34ef7
TG
801 {
802 if (bfd_bread (PRIV (recrd.buf), 1, abfd) != 1)
07d6d2b8
AM
803 {
804 bfd_set_error (bfd_error_file_truncated);
805 return -1;
806 }
95e34ef7
TG
807 }
808
809 /* Read the record header */
ddfb684a 810 if (bfd_bread (PRIV (recrd.buf), test_len, abfd) != test_len)
95e34ef7
TG
811 {
812 bfd_set_error (bfd_error_file_truncated);
813 return -1;
814 }
815
816 /* Reset the record pointer. */
817 PRIV (recrd.rec) = PRIV (recrd.buf);
818 maybe_adjust_record_pointer_for_object (abfd);
819
820 if (vms_get_remaining_object_record (abfd, test_len) <= 0)
821 return -1;
822
823 type = bfd_getl16 (PRIV (recrd.rec));
824
825 vms_debug2 ((8, "_bfd_vms_get_obj_record: rec %p, size %d, type %d\n",
07d6d2b8 826 PRIV (recrd.rec), PRIV (recrd.rec_size), type));
95e34ef7
TG
827
828 return type;
829}
830
831/* Implement step #2 of the object record reading procedure.
832 Return the size of the record or 0 on failure. */
833
834static int
0a9d414a 835vms_get_remaining_object_record (bfd *abfd, unsigned int read_so_far)
95e34ef7
TG
836{
837 unsigned int to_read;
838
839 vms_debug2 ((8, "vms_get_remaining_obj_record\n"));
840
841 /* Extract record size. */
842 PRIV (recrd.rec_size) = bfd_getl16 (PRIV (recrd.rec) + 2);
843
083faca9 844 if (PRIV (recrd.rec_size) == 0)
95e34ef7
TG
845 {
846 bfd_set_error (bfd_error_file_truncated);
847 return 0;
848 }
849
850 /* That's what the linker manual says. */
851 if (PRIV (recrd.rec_size) > EOBJ__C_MAXRECSIZ)
852 {
853 bfd_set_error (bfd_error_file_truncated);
854 return 0;
855 }
856
857 /* Take into account object adjustment. */
858 to_read = PRIV (recrd.rec_size);
859 if (PRIV (recrd.file_format) == FF_FOREIGN)
860 to_read += VMS_OBJECT_ADJUSTMENT;
861
862 /* Adjust the buffer. */
863 if (to_read > PRIV (recrd.buf_size))
864 {
865 PRIV (recrd.buf)
9cb56943 866 = (unsigned char *) bfd_realloc_or_free (PRIV (recrd.buf), to_read);
95e34ef7 867 if (PRIV (recrd.buf) == NULL)
07d6d2b8 868 return 0;
95e34ef7
TG
869 PRIV (recrd.buf_size) = to_read;
870 }
0a9d414a
NC
871 /* PR 17512: file: 025-1974-0.004. */
872 else if (to_read <= read_so_far)
873 return 0;
1b786873 874
95e34ef7
TG
875 /* Read the remaining record. */
876 to_read -= read_so_far;
877
878 vms_debug2 ((8, "vms_get_remaining_obj_record: to_read %d\n", to_read));
879
880 if (bfd_bread (PRIV (recrd.buf) + read_so_far, to_read, abfd) != to_read)
881 {
882 bfd_set_error (bfd_error_file_truncated);
883 return 0;
884 }
885
886 /* Reset the record pointer. */
887 PRIV (recrd.rec) = PRIV (recrd.buf);
888 maybe_adjust_record_pointer_for_object (abfd);
889
890 vms_debug2 ((8, "vms_get_remaining_obj_record: size %d\n",
07d6d2b8 891 PRIV (recrd.rec_size)));
95e34ef7
TG
892
893 return PRIV (recrd.rec_size);
894}
895
896/* Read and process emh record.
897 Return TRUE on success, FALSE on error. */
898
899static bfd_boolean
900_bfd_vms_slurp_ehdr (bfd *abfd)
901{
902 unsigned char *ptr;
903 unsigned char *vms_rec;
4e5cb37e 904 unsigned char *end;
95e34ef7
TG
905 int subtype;
906
907 vms_rec = PRIV (recrd.rec);
4e5cb37e 908 /* PR 17512: file: 62736583. */
8bdf0be1 909 end = PRIV (recrd.buf) + PRIV (recrd.buf_size);
95e34ef7
TG
910
911 vms_debug2 ((2, "HDR/EMH\n"));
912
913 subtype = bfd_getl16 (vms_rec + 4);
914
915 vms_debug2 ((3, "subtype %d\n", subtype));
916
917 switch (subtype)
918 {
919 case EMH__C_MHD:
920 /* Module header. */
4e5cb37e
NC
921 if (vms_rec + 21 >= end)
922 goto fail;
95e34ef7
TG
923 PRIV (hdr_data).hdr_b_strlvl = vms_rec[6];
924 PRIV (hdr_data).hdr_l_arch1 = bfd_getl32 (vms_rec + 8);
925 PRIV (hdr_data).hdr_l_arch2 = bfd_getl32 (vms_rec + 12);
926 PRIV (hdr_data).hdr_l_recsiz = bfd_getl32 (vms_rec + 16);
4e5cb37e
NC
927 if ((vms_rec + 20 + vms_rec[20] + 1) >= end)
928 goto fail;
37d2e9c7
AM
929 PRIV (hdr_data).hdr_t_name
930 = _bfd_vms_save_counted_string (abfd, vms_rec + 20, vms_rec[20]);
95e34ef7 931 ptr = vms_rec + 20 + vms_rec[20] + 1;
4e5cb37e
NC
932 if ((ptr + *ptr + 1) >= end)
933 goto fail;
37d2e9c7
AM
934 PRIV (hdr_data).hdr_t_version
935 = _bfd_vms_save_counted_string (abfd, ptr, *ptr);
95e34ef7 936 ptr += *ptr + 1;
4e5cb37e
NC
937 if (ptr + 17 >= end)
938 goto fail;
37d2e9c7
AM
939 PRIV (hdr_data).hdr_t_date
940 = _bfd_vms_save_sized_string (abfd, ptr, 17);
95e34ef7
TG
941 break;
942
943 case EMH__C_LNM:
4e5cb37e
NC
944 if (vms_rec + PRIV (recrd.rec_size - 6) > end)
945 goto fail;
37d2e9c7
AM
946 PRIV (hdr_data).hdr_c_lnm
947 = _bfd_vms_save_sized_string (abfd, vms_rec, PRIV (recrd.rec_size - 6));
95e34ef7
TG
948 break;
949
950 case EMH__C_SRC:
4e5cb37e
NC
951 if (vms_rec + PRIV (recrd.rec_size - 6) > end)
952 goto fail;
37d2e9c7
AM
953 PRIV (hdr_data).hdr_c_src
954 = _bfd_vms_save_sized_string (abfd, vms_rec, PRIV (recrd.rec_size - 6));
95e34ef7
TG
955 break;
956
957 case EMH__C_TTL:
4e5cb37e
NC
958 if (vms_rec + PRIV (recrd.rec_size - 6) > end)
959 goto fail;
37d2e9c7
AM
960 PRIV (hdr_data).hdr_c_ttl
961 = _bfd_vms_save_sized_string (abfd, vms_rec, PRIV (recrd.rec_size - 6));
95e34ef7
TG
962 break;
963
964 case EMH__C_CPR:
965 case EMH__C_MTC:
966 case EMH__C_GTX:
967 break;
968
969 default:
4e5cb37e 970 fail:
95e34ef7
TG
971 bfd_set_error (bfd_error_wrong_format);
972 return FALSE;
973 }
974
975 return TRUE;
976}
977
978/* Typical sections for evax object files. */
979
980#define EVAX_ABS_NAME "$ABS$"
981#define EVAX_CODE_NAME "$CODE$"
982#define EVAX_LINK_NAME "$LINK$"
983#define EVAX_DATA_NAME "$DATA$"
984#define EVAX_BSS_NAME "$BSS$"
985#define EVAX_READONLYADDR_NAME "$READONLY_ADDR$"
986#define EVAX_READONLY_NAME "$READONLY$"
987#define EVAX_LITERAL_NAME "$LITERAL$"
988#define EVAX_LITERALS_NAME "$LITERALS"
989#define EVAX_COMMON_NAME "$COMMON$"
990#define EVAX_LOCAL_NAME "$LOCAL$"
991
992struct sec_flags_struct
993{
994 const char *name; /* Name of section. */
995 int vflags_always;
996 flagword flags_always; /* Flags we set always. */
997 int vflags_hassize;
998 flagword flags_hassize; /* Flags we set if the section has a size > 0. */
999};
1000
1001/* These flags are deccrtl/vaxcrtl (openVMS 6.2 Alpha) compatible. */
1002
81bb31c0 1003static const struct sec_flags_struct evax_section_flags[] =
95e34ef7
TG
1004 {
1005 { EVAX_ABS_NAME,
d833fa0d
TG
1006 EGPS__V_SHR,
1007 0,
1008 EGPS__V_SHR,
1009 0 },
95e34ef7 1010 { EVAX_CODE_NAME,
d833fa0d 1011 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_EXE,
cf6b8767 1012 SEC_CODE | SEC_READONLY,
d833fa0d 1013 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_EXE,
cf6b8767 1014 SEC_CODE | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1015 { EVAX_LITERAL_NAME,
d833fa0d
TG
1016 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD | EGPS__V_NOMOD,
1017 SEC_DATA | SEC_READONLY,
1018 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD,
cf6b8767 1019 SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1020 { EVAX_LINK_NAME,
d833fa0d
TG
1021 EGPS__V_REL | EGPS__V_RD,
1022 SEC_DATA | SEC_READONLY,
1023 EGPS__V_REL | EGPS__V_RD,
cf6b8767 1024 SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1025 { EVAX_DATA_NAME,
d833fa0d
TG
1026 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD,
1027 SEC_DATA,
1028 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT,
1029 SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1030 { EVAX_BSS_NAME,
d833fa0d
TG
1031 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD,
1032 SEC_NO_FLAGS,
1033 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT | EGPS__V_NOMOD,
1034 SEC_ALLOC },
95e34ef7 1035 { EVAX_READONLYADDR_NAME,
d833fa0d
TG
1036 EGPS__V_PIC | EGPS__V_REL | EGPS__V_RD,
1037 SEC_DATA | SEC_READONLY,
1038 EGPS__V_PIC | EGPS__V_REL | EGPS__V_RD,
cf6b8767 1039 SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1040 { EVAX_READONLY_NAME,
d833fa0d
TG
1041 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD | EGPS__V_NOMOD,
1042 SEC_DATA | SEC_READONLY,
1043 EGPS__V_PIC | EGPS__V_REL | EGPS__V_SHR | EGPS__V_RD,
cf6b8767 1044 SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1045 { EVAX_LOCAL_NAME,
d833fa0d
TG
1046 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT,
1047 SEC_DATA,
1048 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT,
1049 SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1050 { EVAX_LITERALS_NAME,
d833fa0d
TG
1051 EGPS__V_PIC | EGPS__V_OVR,
1052 SEC_DATA | SEC_READONLY,
1053 EGPS__V_PIC | EGPS__V_OVR,
cf6b8767 1054 SEC_DATA | SEC_READONLY | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD },
95e34ef7 1055 { NULL,
d833fa0d
TG
1056 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT,
1057 SEC_DATA,
1058 EGPS__V_REL | EGPS__V_RD | EGPS__V_WRT,
8185f55c 1059 SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD }
95e34ef7
TG
1060 };
1061
81bb31c0 1062/* Retrieve BFD section flags by name and size. */
95e34ef7
TG
1063
1064static flagword
81bb31c0
TG
1065vms_secflag_by_name (const struct sec_flags_struct *section_flags,
1066 const char *name,
95e34ef7
TG
1067 int hassize)
1068{
1069 int i = 0;
1070
1071 while (section_flags[i].name != NULL)
1072 {
1073 if (strcmp (name, section_flags[i].name) == 0)
07d6d2b8 1074 {
95e34ef7
TG
1075 if (hassize)
1076 return section_flags[i].flags_hassize;
1077 else
1078 return section_flags[i].flags_always;
1079 }
1080 i++;
1081 }
1082 if (hassize)
1083 return section_flags[i].flags_hassize;
1084 return section_flags[i].flags_always;
1085}
1086
81bb31c0 1087/* Retrieve VMS section flags by name and size. */
95e34ef7
TG
1088
1089static flagword
81bb31c0
TG
1090vms_esecflag_by_name (const struct sec_flags_struct *section_flags,
1091 const char *name,
07d6d2b8 1092 int hassize)
95e34ef7
TG
1093{
1094 int i = 0;
1095
1096 while (section_flags[i].name != NULL)
1097 {
1098 if (strcmp (name, section_flags[i].name) == 0)
1099 {
1100 if (hassize)
1101 return section_flags[i].vflags_hassize;
1102 else
1103 return section_flags[i].vflags_always;
1104 }
1105 i++;
1106 }
1107 if (hassize)
1108 return section_flags[i].vflags_hassize;
1109 return section_flags[i].vflags_always;
1110}
1111
ce76e55c
TG
1112/* Add SYM to the symbol table of ABFD.
1113 Return FALSE in case of error. */
95e34ef7 1114
ce76e55c
TG
1115static bfd_boolean
1116add_symbol_entry (bfd *abfd, struct vms_symbol_entry *sym)
95e34ef7 1117{
95e34ef7
TG
1118 if (PRIV (gsd_sym_count) >= PRIV (max_sym_count))
1119 {
1120 if (PRIV (max_sym_count) == 0)
07d6d2b8
AM
1121 {
1122 PRIV (max_sym_count) = 128;
1123 PRIV (syms) = bfd_malloc
1124 (PRIV (max_sym_count) * sizeof (struct vms_symbol_entry *));
1125 }
95e34ef7 1126 else
07d6d2b8
AM
1127 {
1128 PRIV (max_sym_count) *= 2;
9cb56943 1129 PRIV (syms) = bfd_realloc_or_free
07d6d2b8
AM
1130 (PRIV (syms),
1131 (PRIV (max_sym_count) * sizeof (struct vms_symbol_entry *)));
1132 }
95e34ef7 1133 if (PRIV (syms) == NULL)
07d6d2b8 1134 return FALSE;
95e34ef7
TG
1135 }
1136
ce76e55c
TG
1137 PRIV (syms)[PRIV (gsd_sym_count)++] = sym;
1138 return TRUE;
1139}
1140
1141/* Create a symbol whose name is ASCIC and add it to ABFD.
1142 Return NULL in case of error. */
1143
1144static struct vms_symbol_entry *
2c0e48e5 1145add_symbol (bfd *abfd, const unsigned char *ascic, unsigned int max)
ce76e55c
TG
1146{
1147 struct vms_symbol_entry *entry;
2c0e48e5 1148 unsigned int len;
ce76e55c
TG
1149
1150 len = *ascic++;
2c0e48e5
AM
1151 max -= 1;
1152 if (len > max)
1153 {
1154 _bfd_error_handler (_("record is too small for symbol name length"));
1155 bfd_set_error (bfd_error_bad_value);
1156 return NULL;
1157 }
1158
ce76e55c
TG
1159 entry = (struct vms_symbol_entry *)bfd_zalloc (abfd, sizeof (*entry) + len);
1160 if (entry == NULL)
1161 return NULL;
1162 entry->namelen = len;
1163 memcpy (entry->name, ascic, len);
1164 entry->name[len] = 0;
1165 entry->owner = abfd;
1166
1167 if (!add_symbol_entry (abfd, entry))
1168 return NULL;
95e34ef7
TG
1169 return entry;
1170}
1171
1172/* Read and process EGSD. Return FALSE on failure. */
1173
1174static bfd_boolean
5fe88cfb 1175_bfd_vms_slurp_egsd (bfd *abfd)
95e34ef7 1176{
72e84f96
NC
1177 int gsd_type;
1178 unsigned int gsd_size;
95e34ef7 1179 unsigned char *vms_rec;
401e101e 1180 bfd_vma base_addr;
bf31e604 1181 long psindx;
95e34ef7
TG
1182
1183 vms_debug2 ((2, "EGSD\n"));
1184
3de58d95
NC
1185 if (PRIV (recrd.rec_size) < 8)
1186 {
38f14ab8 1187 _bfd_error_handler (_("corrupt EGSD record: its size (%#x) is too small"),
3de58d95
NC
1188 PRIV (recrd.rec_size));
1189 bfd_set_error (bfd_error_bad_value);
1190 return FALSE;
1191 }
07d6d2b8 1192
95e34ef7
TG
1193 PRIV (recrd.rec) += 8; /* Skip type, size, align pad. */
1194 PRIV (recrd.rec_size) -= 8;
1195
1196 /* Calculate base address for each section. */
401e101e 1197 base_addr = 0;
95e34ef7 1198
72e84f96 1199 while (PRIV (recrd.rec_size) > 4)
95e34ef7
TG
1200 {
1201 vms_rec = PRIV (recrd.rec);
1202
1203 gsd_type = bfd_getl16 (vms_rec);
1204 gsd_size = bfd_getl16 (vms_rec + 2);
1205
1206 vms_debug2 ((3, "egsd_type %d\n", gsd_type));
1207
72e84f96
NC
1208 /* PR 21615: Check for size overflow. */
1209 if (PRIV (recrd.rec_size) < gsd_size)
1210 {
bf31e604
AM
1211 _bfd_error_handler (_("corrupt EGSD record type %d: size (%#x) "
1212 "is larger than remaining space (%#x)"),
1213 gsd_type, gsd_size, PRIV (recrd.rec_size));
7adc0a81
NC
1214 bfd_set_error (bfd_error_bad_value);
1215 return FALSE;
1216 }
1217
b50ef514
AM
1218 if (gsd_size < 4)
1219 {
1220 too_small:
1221 _bfd_error_handler (_("corrupt EGSD record type %d: size (%#x) "
1222 "is too small"),
1223 gsd_type, gsd_size);
1224 bfd_set_error (bfd_error_bad_value);
1225 return FALSE;
1226 }
1227
95e34ef7
TG
1228 switch (gsd_type)
1229 {
1230 case EGSD__C_PSC:
07d6d2b8 1231 /* Program section definition. */
95e34ef7 1232 {
bf31e604 1233 struct vms_egps *egps = (struct vms_egps *) vms_rec;
07d6d2b8
AM
1234 flagword new_flags, vms_flags;
1235 asection *section;
5fe88cfb 1236
bf31e604 1237 if (offsetof (struct vms_egps, flags) + 2 > gsd_size)
b50ef514 1238 goto too_small;
8185f55c 1239 vms_flags = bfd_getl16 (egps->flags);
21e003e8 1240
07d6d2b8
AM
1241 if ((vms_flags & EGPS__V_REL) == 0)
1242 {
1243 /* Use the global absolute section for all
1244 absolute sections. */
1245 section = bfd_abs_section_ptr;
1246 }
1247 else
1248 {
1249 char *name;
401e101e 1250 bfd_vma align_addr;
bf31e604 1251 size_t left;
21e003e8 1252
bf31e604
AM
1253 if (offsetof (struct vms_egps, namlng) >= gsd_size)
1254 goto too_small;
1255 left = gsd_size - offsetof (struct vms_egps, namlng);
1256 name = _bfd_vms_save_counted_string (abfd, &egps->namlng, left);
1257 if (name == NULL || name[0] == 0)
1258 return FALSE;
21e003e8 1259
07d6d2b8
AM
1260 section = bfd_make_section (abfd, name);
1261 if (!section)
1262 return FALSE;
1263
1264 section->filepos = 0;
1265 section->size = bfd_getl32 (egps->alloc);
401e101e 1266 section->alignment_power = egps->align & 31;
07d6d2b8
AM
1267
1268 vms_section_data (section)->flags = vms_flags;
1269 vms_section_data (section)->no_flags = 0;
1270
37d2e9c7
AM
1271 new_flags = vms_secflag_by_name (evax_section_flags,
1272 section->name,
07d6d2b8
AM
1273 section->size > 0);
1274 if (section->size > 0)
1275 new_flags |= SEC_LOAD;
1276 if (!(vms_flags & EGPS__V_NOMOD) && section->size > 0)
1277 {
1278 /* Set RELOC and HAS_CONTENTS if the section is not
1279 demand-zero and not empty. */
1280 new_flags |= SEC_HAS_CONTENTS;
1281 if (vms_flags & EGPS__V_REL)
1282 new_flags |= SEC_RELOC;
1283 }
1284 if (vms_flags & EGPS__V_EXE)
1285 {
1286 /* Set CODE if section is executable. */
1287 new_flags |= SEC_CODE;
1288 new_flags &= ~SEC_DATA;
1289 }
fd361982 1290 if (!bfd_set_section_flags (section, new_flags))
07d6d2b8
AM
1291 return FALSE;
1292
1293 /* Give a non-overlapping vma to non absolute sections. */
401e101e
AM
1294 align_addr = (bfd_vma) 1 << section->alignment_power;
1295 base_addr = (base_addr + align_addr - 1) & -align_addr;
1296 section->vma = base_addr;
07d6d2b8
AM
1297 base_addr += section->size;
1298 }
1299
1300 /* Append it to the section array. */
1301 if (PRIV (section_count) >= PRIV (section_max))
1302 {
1303 if (PRIV (section_max) == 0)
1304 PRIV (section_max) = 16;
1305 else
1306 PRIV (section_max) *= 2;
1307 PRIV (sections) = bfd_realloc_or_free
1308 (PRIV (sections), PRIV (section_max) * sizeof (asection *));
1309 if (PRIV (sections) == NULL)
1310 return FALSE;
1311 }
1312
1313 PRIV (sections)[PRIV (section_count)] = section;
1314 PRIV (section_count)++;
95e34ef7
TG
1315 }
1316 break;
1317
1318 case EGSD__C_SYM:
1319 {
2c0e48e5 1320 unsigned int nameoff;
07d6d2b8
AM
1321 struct vms_symbol_entry *entry;
1322 struct vms_egsy *egsy = (struct vms_egsy *) vms_rec;
1323 flagword old_flags;
95e34ef7 1324
bf31e604
AM
1325 if (offsetof (struct vms_egsy, flags) + 2 > gsd_size)
1326 goto too_small;
95e34ef7
TG
1327 old_flags = bfd_getl16 (egsy->flags);
1328 if (old_flags & EGSY__V_DEF)
07d6d2b8
AM
1329 nameoff = ESDF__B_NAMLNG;
1330 else
1331 nameoff = ESRF__B_NAMLNG;
95e34ef7 1332
2c0e48e5 1333 if (nameoff >= gsd_size)
bf31e604 1334 goto too_small;
2c0e48e5 1335 entry = add_symbol (abfd, vms_rec + nameoff, gsd_size - nameoff);
07d6d2b8
AM
1336 if (entry == NULL)
1337 return FALSE;
95e34ef7 1338
07d6d2b8
AM
1339 /* Allow only duplicate reference. */
1340 if ((entry->flags & EGSY__V_DEF) && (old_flags & EGSY__V_DEF))
1341 abort ();
95e34ef7 1342
07d6d2b8
AM
1343 if (entry->typ == 0)
1344 {
1345 entry->typ = gsd_type;
1346 entry->data_type = egsy->datyp;
1347 entry->flags = old_flags;
1348 }
95e34ef7
TG
1349
1350 if (old_flags & EGSY__V_DEF)
07d6d2b8 1351 {
bf31e604 1352 struct vms_esdf *esdf = (struct vms_esdf *) vms_rec;
95e34ef7
TG
1353
1354 entry->value = bfd_getl64 (esdf->value);
cb06d03a
NC
1355 if (PRIV (sections) == NULL)
1356 return FALSE;
ca4cf9b9
NC
1357
1358 psindx = bfd_getl32 (esdf->psindx);
1359 /* PR 21813: Check for an out of range index. */
1360 if (psindx < 0 || psindx >= (int) PRIV (section_count))
1361 {
bf31e604
AM
1362 bad_psindx:
1363 _bfd_error_handler (_("corrupt EGSD record: its psindx "
1364 "field is too big (%#lx)"),
ca4cf9b9
NC
1365 psindx);
1366 bfd_set_error (bfd_error_bad_value);
1367 return FALSE;
1368 }
1369 entry->section = PRIV (sections)[psindx];
95e34ef7 1370
07d6d2b8
AM
1371 if (old_flags & EGSY__V_NORM)
1372 {
1373 PRIV (norm_sym_count)++;
95e34ef7 1374
07d6d2b8 1375 entry->code_value = bfd_getl64 (esdf->code_address);
ca4cf9b9 1376 psindx = bfd_getl32 (esdf->ca_psindx);
bf31e604 1377 /* PR 21813: Check for an out of range index. */
ca4cf9b9 1378 if (psindx < 0 || psindx >= (int) PRIV (section_count))
bf31e604 1379 goto bad_psindx;
07d6d2b8
AM
1380 entry->code_section = PRIV (sections)[psindx];
1381 }
1382 }
95e34ef7
TG
1383 }
1384 break;
1385
1386 case EGSD__C_SYMG:
1387 {
07d6d2b8
AM
1388 struct vms_symbol_entry *entry;
1389 struct vms_egst *egst = (struct vms_egst *)vms_rec;
1390 flagword old_flags;
2c0e48e5 1391 unsigned int nameoff = offsetof (struct vms_egst, namlng);
95e34ef7
TG
1392
1393 old_flags = bfd_getl16 (egst->header.flags);
95e34ef7 1394
2c0e48e5 1395 if (nameoff >= gsd_size)
bf31e604 1396 goto too_small;
2c0e48e5 1397 entry = add_symbol (abfd, &egst->namlng, gsd_size - nameoff);
07d6d2b8
AM
1398 if (entry == NULL)
1399 return FALSE;
95e34ef7 1400
07d6d2b8
AM
1401 entry->typ = gsd_type;
1402 entry->data_type = egst->header.datyp;
1403 entry->flags = old_flags;
95e34ef7 1404
07d6d2b8 1405 entry->symbol_vector = bfd_getl32 (egst->value);
95e34ef7 1406
07d6d2b8 1407 if (old_flags & EGSY__V_REL)
cb06d03a
NC
1408 {
1409 if (PRIV (sections) == NULL)
1410 return FALSE;
ca4cf9b9
NC
1411 psindx = bfd_getl32 (egst->psindx);
1412 /* PR 21813: Check for an out of range index. */
1413 if (psindx < 0 || psindx >= (int) PRIV (section_count))
bf31e604 1414 goto bad_psindx;
ca4cf9b9 1415 entry->section = PRIV (sections)[psindx];
cb06d03a 1416 }
07d6d2b8
AM
1417 else
1418 entry->section = bfd_abs_section_ptr;
a928f1d7 1419
07d6d2b8 1420 entry->value = bfd_getl64 (egst->lp_2);
95e34ef7 1421
07d6d2b8
AM
1422 if (old_flags & EGSY__V_NORM)
1423 {
1424 PRIV (norm_sym_count)++;
95e34ef7 1425
07d6d2b8
AM
1426 entry->code_value = bfd_getl64 (egst->lp_1);
1427 entry->code_section = bfd_abs_section_ptr;
1428 }
1429 }
95e34ef7
TG
1430 break;
1431
07d6d2b8
AM
1432 case EGSD__C_SPSC:
1433 case EGSD__C_IDC:
1434 /* Currently ignored. */
1435 break;
95e34ef7
TG
1436 case EGSD__C_SYMM:
1437 case EGSD__C_SYMV:
1438 default:
38f14ab8 1439 _bfd_error_handler (_("unknown EGSD subtype %d"), gsd_type);
95e34ef7
TG
1440 bfd_set_error (bfd_error_bad_value);
1441 return FALSE;
1442 }
1443
1444 PRIV (recrd.rec_size) -= gsd_size;
1445 PRIV (recrd.rec) += gsd_size;
1446 }
1447
3de58d95
NC
1448 /* FIXME: Should we complain if PRIV (recrd.rec_size) is not zero ? */
1449
95e34ef7
TG
1450 if (PRIV (gsd_sym_count) > 0)
1451 abfd->flags |= HAS_SYMS;
1452
1453 return TRUE;
1454}
1455
1456/* Stack routines for vms ETIR commands. */
1457
1458/* Push value and section index. */
1459
ab356be7 1460static bfd_boolean
95e34ef7
TG
1461_bfd_vms_push (bfd *abfd, bfd_vma val, unsigned int reloc)
1462{
1463 vms_debug2 ((4, "<push %08lx (0x%08x) at %d>\n",
07d6d2b8 1464 (unsigned long)val, reloc, PRIV (stackptr)));
95e34ef7
TG
1465
1466 PRIV (stack[PRIV (stackptr)]).value = val;
1467 PRIV (stack[PRIV (stackptr)]).reloc = reloc;
1468 PRIV (stackptr)++;
1469 if (PRIV (stackptr) >= STACKSIZE)
1470 {
1471 bfd_set_error (bfd_error_bad_value);
38f14ab8 1472 _bfd_error_handler (_("stack overflow (%d) in _bfd_vms_push"), PRIV (stackptr));
ab356be7 1473 return FALSE;
95e34ef7 1474 }
ab356be7 1475 return TRUE;
95e34ef7
TG
1476}
1477
1478/* Pop value and section index. */
1479
ab356be7 1480static bfd_boolean
95e34ef7
TG
1481_bfd_vms_pop (bfd *abfd, bfd_vma *val, unsigned int *rel)
1482{
1483 if (PRIV (stackptr) == 0)
1484 {
1485 bfd_set_error (bfd_error_bad_value);
38f14ab8 1486 _bfd_error_handler (_("stack underflow in _bfd_vms_pop"));
ab356be7 1487 return FALSE;
95e34ef7
TG
1488 }
1489 PRIV (stackptr)--;
1490 *val = PRIV (stack[PRIV (stackptr)]).value;
1491 *rel = PRIV (stack[PRIV (stackptr)]).reloc;
1492
1493 vms_debug2 ((4, "<pop %08lx (0x%08x)>\n", (unsigned long)*val, *rel));
ab356be7 1494 return TRUE;
95e34ef7
TG
1495}
1496
1497/* Routines to fill sections contents during tir/etir read. */
1498
1499/* Initialize image buffer pointer to be filled. */
1500
1501static void
1502image_set_ptr (bfd *abfd, bfd_vma vma, int sect, struct bfd_link_info *info)
1503{
1504 asection *sec;
1505
1506 vms_debug2 ((4, "image_set_ptr (0x%08x, sect=%d)\n", (unsigned)vma, sect));
1507
cb06d03a
NC
1508 if (PRIV (sections) == NULL)
1509 return;
ca4cf9b9
NC
1510 if (sect < 0 || sect >= (int) PRIV (section_count))
1511 return;
1512
95e34ef7
TG
1513 sec = PRIV (sections)[sect];
1514
1515 if (info)
1516 {
1517 /* Reading contents to an output bfd. */
1518
1519 if (sec->output_section == NULL)
07d6d2b8
AM
1520 {
1521 /* Section discarded. */
1522 vms_debug2 ((5, " section %s discarded\n", sec->name));
1523
1524 /* This is not used. */
1525 PRIV (image_section) = NULL;
1526 PRIV (image_offset) = 0;
1527 return;
1528 }
95e34ef7
TG
1529 PRIV (image_offset) = sec->output_offset + vma;
1530 PRIV (image_section) = sec->output_section;
1531 }
1532 else
1533 {
1534 PRIV (image_offset) = vma;
1535 PRIV (image_section) = sec;
1536 }
1537}
1538
1539/* Increment image buffer pointer by offset. */
1540
1541static void
1542image_inc_ptr (bfd *abfd, bfd_vma offset)
1543{
1544 vms_debug2 ((4, "image_inc_ptr (%u)\n", (unsigned)offset));
1545
1546 PRIV (image_offset) += offset;
1547}
1548
1549/* Save current DST location counter under specified index. */
1550
9cb56943 1551static bfd_boolean
95e34ef7
TG
1552dst_define_location (bfd *abfd, unsigned int loc)
1553{
1554 vms_debug2 ((4, "dst_define_location (%d)\n", (int)loc));
1555
f75fbe8a
AM
1556 if (loc > 1 << 24)
1557 {
1558 /* 16M entries ought to be plenty. */
1559 bfd_set_error (bfd_error_bad_value);
1560 _bfd_error_handler (_("dst_define_location %u too large"), loc);
1561 return FALSE;
1562 }
1563
95e34ef7
TG
1564 /* Grow the ptr offset table if necessary. */
1565 if (loc + 1 > PRIV (dst_ptr_offsets_count))
1566 {
9cb56943
AM
1567 PRIV (dst_ptr_offsets)
1568 = bfd_realloc_or_free (PRIV (dst_ptr_offsets),
1569 (loc + 1) * sizeof (unsigned int));
1570 if (PRIV (dst_ptr_offsets) == NULL)
1571 return FALSE;
95e34ef7
TG
1572 PRIV (dst_ptr_offsets_count) = loc + 1;
1573 }
1574
1575 PRIV (dst_ptr_offsets)[loc] = PRIV (image_offset);
9cb56943 1576 return TRUE;
95e34ef7
TG
1577}
1578
1579/* Restore saved DST location counter from specified index. */
1580
7bac4137 1581static bfd_boolean
95e34ef7
TG
1582dst_restore_location (bfd *abfd, unsigned int loc)
1583{
1584 vms_debug2 ((4, "dst_restore_location (%d)\n", (int)loc));
1585
7bac4137
AM
1586 if (loc < PRIV (dst_ptr_offsets_count))
1587 {
1588 PRIV (image_offset) = PRIV (dst_ptr_offsets)[loc];
1589 return TRUE;
1590 }
1591 return FALSE;
95e34ef7
TG
1592}
1593
1594/* Retrieve saved DST location counter from specified index. */
1595
7bac4137
AM
1596static bfd_boolean
1597dst_retrieve_location (bfd *abfd, bfd_vma *loc)
95e34ef7 1598{
7bac4137 1599 vms_debug2 ((4, "dst_retrieve_location (%d)\n", (int) *loc));
95e34ef7 1600
7bac4137
AM
1601 if (*loc < PRIV (dst_ptr_offsets_count))
1602 {
1603 *loc = PRIV (dst_ptr_offsets)[*loc];
1604 return TRUE;
1605 }
1606 return FALSE;
95e34ef7
TG
1607}
1608
95e34ef7
TG
1609/* Write multiple bytes to section image. */
1610
1611static bfd_boolean
c53d2e6d 1612image_write (bfd *abfd, unsigned char *ptr, unsigned int size)
95e34ef7 1613{
81699544
AM
1614 asection *sec = PRIV (image_section);
1615 size_t off = PRIV (image_offset);
1616
1617 /* Check bounds. */
1618 if (off > sec->size
1619 || size > sec->size - off)
1620 {
1621 bfd_set_error (bfd_error_bad_value);
1622 return FALSE;
1623 }
1624
95e34ef7
TG
1625#if VMS_DEBUG
1626 _bfd_vms_debug (8, "image_write from (%p, %d) to (%ld)\n", ptr, size,
81699544 1627 (long) off));
95e34ef7
TG
1628#endif
1629
95e34ef7 1630 if (PRIV (image_section)->contents != NULL)
81699544
AM
1631 memcpy (sec->contents + off, ptr, size);
1632 else
95e34ef7 1633 {
81699544
AM
1634 unsigned int i;
1635 for (i = 0; i < size; i++)
1636 if (ptr[i] != 0)
1637 {
1638 bfd_set_error (bfd_error_bad_value);
1639 return FALSE;
1640 }
95e34ef7 1641 }
81699544 1642
8ab484c2
AM
1643#if VMS_DEBUG
1644 _bfd_hexdump (9, ptr, size, 0);
1645#endif
95e34ef7
TG
1646
1647 PRIV (image_offset) += size;
1648 return TRUE;
1649}
1650
1651/* Write byte to section image. */
1652
1653static bfd_boolean
1654image_write_b (bfd * abfd, unsigned int value)
1655{
1656 unsigned char data[1];
1657
1658 vms_debug2 ((6, "image_write_b (%02x)\n", (int) value));
1659
1660 *data = value;
1661
1662 return image_write (abfd, data, sizeof (data));
1663}
1664
1665/* Write 2-byte word to image. */
1666
1667static bfd_boolean
1668image_write_w (bfd * abfd, unsigned int value)
1669{
1670 unsigned char data[2];
1671
1672 vms_debug2 ((6, "image_write_w (%04x)\n", (int) value));
1673
1674 bfd_putl16 (value, data);
1675 return image_write (abfd, data, sizeof (data));
1676}
1677
1678/* Write 4-byte long to image. */
1679
1680static bfd_boolean
1681image_write_l (bfd * abfd, unsigned long value)
1682{
1683 unsigned char data[4];
1684
1685 vms_debug2 ((6, "image_write_l (%08lx)\n", value));
1686
1687 bfd_putl32 (value, data);
1688 return image_write (abfd, data, sizeof (data));
1689}
1690
1691/* Write 8-byte quad to image. */
1692
1693static bfd_boolean
1694image_write_q (bfd * abfd, bfd_vma value)
1695{
1696 unsigned char data[8];
1697
1698 vms_debug2 ((6, "image_write_q (%08lx)\n", (unsigned long)value));
1699
1700 bfd_putl64 (value, data);
1701 return image_write (abfd, data, sizeof (data));
1702}
1703\f
1704static const char *
1705_bfd_vms_etir_name (int cmd)
1706{
1707 switch (cmd)
1708 {
1709 case ETIR__C_STA_GBL: return "ETIR__C_STA_GBL";
1710 case ETIR__C_STA_LW: return "ETIR__C_STA_LW";
1711 case ETIR__C_STA_QW: return "ETIR__C_STA_QW";
1712 case ETIR__C_STA_PQ: return "ETIR__C_STA_PQ";
1713 case ETIR__C_STA_LI: return "ETIR__C_STA_LI";
1714 case ETIR__C_STA_MOD: return "ETIR__C_STA_MOD";
1715 case ETIR__C_STA_CKARG: return "ETIR__C_STA_CKARG";
1716 case ETIR__C_STO_B: return "ETIR__C_STO_B";
1717 case ETIR__C_STO_W: return "ETIR__C_STO_W";
1718 case ETIR__C_STO_GBL: return "ETIR__C_STO_GBL";
1719 case ETIR__C_STO_CA: return "ETIR__C_STO_CA";
1720 case ETIR__C_STO_RB: return "ETIR__C_STO_RB";
1721 case ETIR__C_STO_AB: return "ETIR__C_STO_AB";
1722 case ETIR__C_STO_OFF: return "ETIR__C_STO_OFF";
1723 case ETIR__C_STO_IMM: return "ETIR__C_STO_IMM";
1724 case ETIR__C_STO_IMMR: return "ETIR__C_STO_IMMR";
1725 case ETIR__C_STO_LW: return "ETIR__C_STO_LW";
1726 case ETIR__C_STO_QW: return "ETIR__C_STO_QW";
1727 case ETIR__C_STO_GBL_LW: return "ETIR__C_STO_GBL_LW";
1728 case ETIR__C_STO_LP_PSB: return "ETIR__C_STO_LP_PSB";
1729 case ETIR__C_STO_HINT_GBL: return "ETIR__C_STO_HINT_GBL";
1730 case ETIR__C_STO_HINT_PS: return "ETIR__C_STO_HINT_PS";
1731 case ETIR__C_OPR_ADD: return "ETIR__C_OPR_ADD";
1732 case ETIR__C_OPR_SUB: return "ETIR__C_OPR_SUB";
1733 case ETIR__C_OPR_INSV: return "ETIR__C_OPR_INSV";
1734 case ETIR__C_OPR_USH: return "ETIR__C_OPR_USH";
1735 case ETIR__C_OPR_ROT: return "ETIR__C_OPR_ROT";
1736 case ETIR__C_OPR_REDEF: return "ETIR__C_OPR_REDEF";
1737 case ETIR__C_OPR_DFLIT: return "ETIR__C_OPR_DFLIT";
1738 case ETIR__C_STC_LP: return "ETIR__C_STC_LP";
1739 case ETIR__C_STC_GBL: return "ETIR__C_STC_GBL";
1740 case ETIR__C_STC_GCA: return "ETIR__C_STC_GCA";
1741 case ETIR__C_STC_PS: return "ETIR__C_STC_PS";
1742 case ETIR__C_STC_NBH_PS: return "ETIR__C_STC_NBH_PS";
1743 case ETIR__C_STC_NOP_GBL: return "ETIR__C_STC_NOP_GBL";
1744 case ETIR__C_STC_NOP_PS: return "ETIR__C_STC_NOP_PS";
1745 case ETIR__C_STC_BSR_GBL: return "ETIR__C_STC_BSR_GBL";
1746 case ETIR__C_STC_BSR_PS: return "ETIR__C_STC_BSR_PS";
1747 case ETIR__C_STC_LDA_GBL: return "ETIR__C_STC_LDA_GBL";
1748 case ETIR__C_STC_LDA_PS: return "ETIR__C_STC_LDA_PS";
1749 case ETIR__C_STC_BOH_GBL: return "ETIR__C_STC_BOH_GBL";
1750 case ETIR__C_STC_BOH_PS: return "ETIR__C_STC_BOH_PS";
1751 case ETIR__C_STC_NBH_GBL: return "ETIR__C_STC_NBH_GBL";
1752 case ETIR__C_STC_LP_PSB: return "ETIR__C_STC_LP_PSB";
1753 case ETIR__C_CTL_SETRB: return "ETIR__C_CTL_SETRB";
1754 case ETIR__C_CTL_AUGRB: return "ETIR__C_CTL_AUGRB";
1755 case ETIR__C_CTL_DFLOC: return "ETIR__C_CTL_DFLOC";
1756 case ETIR__C_CTL_STLOC: return "ETIR__C_CTL_STLOC";
1757 case ETIR__C_CTL_STKDL: return "ETIR__C_CTL_STKDL";
1758
1759 default:
1760 /* These names have not yet been added to this switch statement. */
4eca0228 1761 _bfd_error_handler (_("unknown ETIR command %d"), cmd);
95e34ef7
TG
1762 }
1763
1764 return NULL;
1765}
1766#define HIGHBIT(op) ((op & 0x80000000L) == 0x80000000L)
1767
1768static void
c53d2e6d
NC
1769_bfd_vms_get_value (bfd *abfd,
1770 const unsigned char *ascic,
1771 const unsigned char *max_ascic,
07d6d2b8
AM
1772 struct bfd_link_info *info,
1773 bfd_vma *vma,
1774 struct alpha_vms_link_hash_entry **hp)
95e34ef7
TG
1775{
1776 char name[257];
c53d2e6d
NC
1777 unsigned int len;
1778 unsigned int i;
95e34ef7
TG
1779 struct alpha_vms_link_hash_entry *h;
1780
1781 /* Not linking. Do not try to resolve the symbol. */
1782 if (info == NULL)
1783 {
1784 *vma = 0;
1785 *hp = NULL;
1786 return;
1787 }
1788
1789 len = *ascic;
c53d2e6d
NC
1790 if (ascic + len >= max_ascic)
1791 {
38f14ab8 1792 _bfd_error_handler (_("corrupt vms value"));
c53d2e6d
NC
1793 *vma = 0;
1794 *hp = NULL;
1795 return;
1796 }
1797
95e34ef7
TG
1798 for (i = 0; i < len; i++)
1799 name[i] = ascic[i + 1];
1800 name[i] = 0;
1801
1802 h = (struct alpha_vms_link_hash_entry *)
1803 bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
1804
1805 *hp = h;
1806
1807 if (h != NULL
1808 && (h->root.type == bfd_link_hash_defined
07d6d2b8 1809 || h->root.type == bfd_link_hash_defweak))
95e34ef7
TG
1810 *vma = h->root.u.def.value
1811 + h->root.u.def.section->output_offset
1812 + h->root.u.def.section->output_section->vma;
1813 else if (h && h->root.type == bfd_link_hash_undefweak)
1814 *vma = 0;
1815 else
1816 {
1a72702b
AM
1817 (*info->callbacks->undefined_symbol)
1818 (info, name, abfd, PRIV (image_section), PRIV (image_offset), TRUE);
95e34ef7
TG
1819 *vma = 0;
1820 }
1821}
1822
1823#define RELC_NONE 0
1824#define RELC_REL 1
1825#define RELC_SHR_BASE 0x10000
1826#define RELC_SEC_BASE 0x20000
1827#define RELC_MASK 0x0ffff
1828
1829static unsigned int
1830alpha_vms_sym_to_ctxt (struct alpha_vms_link_hash_entry *h)
1831{
1832 /* Handle undefined symbols. */
1833 if (h == NULL || h->sym == NULL)
1834 return RELC_NONE;
1835
1836 if (h->sym->typ == EGSD__C_SYMG)
1837 {
1838 if (h->sym->flags & EGSY__V_REL)
07d6d2b8 1839 return RELC_SHR_BASE + PRIV2 (h->sym->owner, shr_index);
95e34ef7 1840 else
07d6d2b8
AM
1841 {
1842 /* Can this happen (non-relocatable symg) ? I'd like to see
1843 an example. */
1844 abort ();
1845 }
95e34ef7
TG
1846 }
1847 if (h->sym->typ == EGSD__C_SYM)
1848 {
1849 if (h->sym->flags & EGSY__V_REL)
07d6d2b8 1850 return RELC_REL;
95e34ef7 1851 else
07d6d2b8 1852 return RELC_NONE;
95e34ef7
TG
1853 }
1854 abort ();
1855}
1856
1857static bfd_vma
a928f1d7 1858alpha_vms_get_sym_value (asection *sect, bfd_vma addr)
95e34ef7 1859{
a928f1d7 1860 return sect->output_section->vma + sect->output_offset + addr;
95e34ef7
TG
1861}
1862
1863static bfd_vma
1864alpha_vms_fix_sec_rel (bfd *abfd, struct bfd_link_info *info,
07d6d2b8 1865 unsigned int rel, bfd_vma vma)
95e34ef7 1866{
cb06d03a
NC
1867 asection *sec;
1868
1869 if (PRIV (sections) == NULL)
1870 return 0;
1871
1872 sec = PRIV (sections)[rel & RELC_MASK];
95e34ef7
TG
1873
1874 if (info)
1875 {
1876 if (sec->output_section == NULL)
07d6d2b8 1877 abort ();
95e34ef7
TG
1878 return vma + sec->output_section->vma + sec->output_offset;
1879 }
1880 else
1881 return vma + sec->vma;
1882}
1883
44273c5b
TG
1884/* Read an ETIR record from ABFD. If INFO is not null, put the content into
1885 the output section (used during linking).
1886 Return FALSE in case of error. */
1887
95e34ef7
TG
1888static bfd_boolean
1889_bfd_vms_slurp_etir (bfd *abfd, struct bfd_link_info *info)
1890{
1891 unsigned char *ptr;
1892 unsigned int length;
1893 unsigned char *maxptr;
8ab484c2
AM
1894 bfd_vma op1 = 0;
1895 bfd_vma op2 = 0;
1896 unsigned int rel1 = RELC_NONE;
1897 unsigned int rel2 = RELC_NONE;
95e34ef7
TG
1898 struct alpha_vms_link_hash_entry *h;
1899
1900 PRIV (recrd.rec) += ETIR__C_HEADER_SIZE;
1901 PRIV (recrd.rec_size) -= ETIR__C_HEADER_SIZE;
1902
1903 ptr = PRIV (recrd.rec);
1904 length = PRIV (recrd.rec_size);
1905 maxptr = ptr + length;
1906
1907 vms_debug2 ((2, "ETIR: %d bytes\n", length));
1908
1909 while (ptr < maxptr)
1910 {
2c0e48e5 1911 int cmd, cmd_length;
95e34ef7 1912
2c0e48e5
AM
1913 if (ptr + 4 > maxptr)
1914 goto corrupt_etir;
1915
1916 cmd = bfd_getl16 (ptr);
1917 cmd_length = bfd_getl16 (ptr + 2);
95e34ef7 1918
76800cba 1919 /* PR 21589 and 21579: Check for a corrupt ETIR record. */
2c0e48e5 1920 if (cmd_length < 4 || ptr + cmd_length > maxptr)
c53d2e6d
NC
1921 {
1922 corrupt_etir:
38f14ab8 1923 _bfd_error_handler (_("corrupt ETIR record encountered"));
c53d2e6d
NC
1924 bfd_set_error (bfd_error_bad_value);
1925 return FALSE;
1926 }
2c0e48e5 1927 ptr += 4;
c53d2e6d 1928
76800cba
NC
1929#if VMS_DEBUG
1930 _bfd_vms_debug (4, "etir: %s(%d)\n",
07d6d2b8 1931 _bfd_vms_etir_name (cmd), cmd);
76800cba
NC
1932 _bfd_hexdump (8, ptr, cmd_length - 4, 0);
1933#endif
1934
95e34ef7 1935 switch (cmd)
07d6d2b8
AM
1936 {
1937 /* Stack global
1938 arg: cs symbol name
95e34ef7 1939
07d6d2b8
AM
1940 stack 32 bit value of symbol (high bits set to 0). */
1941 case ETIR__C_STA_GBL:
1942 _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
ab356be7
AM
1943 if (!_bfd_vms_push (abfd, op1, alpha_vms_sym_to_ctxt (h)))
1944 return FALSE;
07d6d2b8 1945 break;
95e34ef7 1946
07d6d2b8
AM
1947 /* Stack longword
1948 arg: lw value
95e34ef7 1949
07d6d2b8
AM
1950 stack 32 bit value, sign extend to 64 bit. */
1951 case ETIR__C_STA_LW:
2c0e48e5 1952 if (ptr + 4 > maxptr)
c53d2e6d 1953 goto corrupt_etir;
ab356be7
AM
1954 if (!_bfd_vms_push (abfd, bfd_getl32 (ptr), RELC_NONE))
1955 return FALSE;
07d6d2b8 1956 break;
95e34ef7 1957
07d6d2b8
AM
1958 /* Stack quadword
1959 arg: qw value
95e34ef7 1960
07d6d2b8
AM
1961 stack 64 bit value of symbol. */
1962 case ETIR__C_STA_QW:
2c0e48e5 1963 if (ptr + 8 > maxptr)
c53d2e6d 1964 goto corrupt_etir;
ab356be7
AM
1965 if (!_bfd_vms_push (abfd, bfd_getl64 (ptr), RELC_NONE))
1966 return FALSE;
07d6d2b8 1967 break;
95e34ef7 1968
07d6d2b8
AM
1969 /* Stack psect base plus quadword offset
1970 arg: lw section index
1971 qw signed quadword offset (low 32 bits)
95e34ef7 1972
07d6d2b8
AM
1973 Stack qw argument and section index
1974 (see ETIR__C_STO_OFF, ETIR__C_CTL_SETRB). */
1975 case ETIR__C_STA_PQ:
1976 {
1977 int psect;
95e34ef7 1978
2c0e48e5 1979 if (ptr + 12 > maxptr)
c53d2e6d 1980 goto corrupt_etir;
07d6d2b8
AM
1981 psect = bfd_getl32 (ptr);
1982 if ((unsigned int) psect >= PRIV (section_count))
1983 {
4eca0228
AM
1984 _bfd_error_handler (_("bad section index in %s"),
1985 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
1986 bfd_set_error (bfd_error_bad_value);
1987 return FALSE;
1988 }
1989 op1 = bfd_getl64 (ptr + 4);
ab356be7
AM
1990 if (!_bfd_vms_push (abfd, op1, psect | RELC_SEC_BASE))
1991 return FALSE;
07d6d2b8
AM
1992 }
1993 break;
1994
1995 case ETIR__C_STA_LI:
1996 case ETIR__C_STA_MOD:
1997 case ETIR__C_STA_CKARG:
4eca0228
AM
1998 _bfd_error_handler (_("unsupported STA cmd %s"),
1999 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2000 return FALSE;
2001 break;
2002
2003 /* Store byte: pop stack, write byte
2004 arg: -. */
2005 case ETIR__C_STO_B:
ab356be7
AM
2006 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2007 return FALSE;
07d6d2b8
AM
2008 if (rel1 != RELC_NONE)
2009 goto bad_context;
81699544
AM
2010 if (!image_write_b (abfd, (unsigned int) op1 & 0xff))
2011 return FALSE;
07d6d2b8
AM
2012 break;
2013
2014 /* Store word: pop stack, write word
2015 arg: -. */
2016 case ETIR__C_STO_W:
ab356be7
AM
2017 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2018 return FALSE;
07d6d2b8
AM
2019 if (rel1 != RELC_NONE)
2020 goto bad_context;
81699544
AM
2021 if (!image_write_w (abfd, (unsigned int) op1 & 0xffff))
2022 return FALSE;
07d6d2b8
AM
2023 break;
2024
2025 /* Store longword: pop stack, write longword
2026 arg: -. */
2027 case ETIR__C_STO_LW:
ab356be7
AM
2028 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2029 return FALSE;
07d6d2b8
AM
2030 if (rel1 & RELC_SEC_BASE)
2031 {
2032 op1 = alpha_vms_fix_sec_rel (abfd, info, rel1, op1);
2033 rel1 = RELC_REL;
2034 }
2035 else if (rel1 & RELC_SHR_BASE)
2036 {
96d3b80f
AM
2037 if (!alpha_vms_add_fixup_lr (info, rel1 & RELC_MASK, op1))
2038 return FALSE;
07d6d2b8
AM
2039 rel1 = RELC_NONE;
2040 }
2041 if (rel1 != RELC_NONE)
2042 {
2043 if (rel1 != RELC_REL)
2044 abort ();
96d3b80f
AM
2045 if (!alpha_vms_add_lw_reloc (info))
2046 return FALSE;
07d6d2b8 2047 }
81699544
AM
2048 if (!image_write_l (abfd, op1))
2049 return FALSE;
07d6d2b8
AM
2050 break;
2051
2052 /* Store quadword: pop stack, write quadword
2053 arg: -. */
2054 case ETIR__C_STO_QW:
ab356be7
AM
2055 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2056 return FALSE;
07d6d2b8
AM
2057 if (rel1 & RELC_SEC_BASE)
2058 {
2059 op1 = alpha_vms_fix_sec_rel (abfd, info, rel1, op1);
2060 rel1 = RELC_REL;
2061 }
2062 else if (rel1 & RELC_SHR_BASE)
2063 abort ();
2064 if (rel1 != RELC_NONE)
2065 {
2066 if (rel1 != RELC_REL)
2067 abort ();
96d3b80f
AM
2068 if (!alpha_vms_add_qw_reloc (info))
2069 return FALSE;
07d6d2b8 2070 }
81699544
AM
2071 if (!image_write_q (abfd, op1))
2072 return FALSE;
07d6d2b8
AM
2073 break;
2074
2075 /* Store immediate repeated: pop stack for repeat count
2076 arg: lw byte count
2077 da data. */
2078 case ETIR__C_STO_IMMR:
2079 {
2080 int size;
95e34ef7 2081
2c0e48e5 2082 if (ptr + 4 > maxptr)
c53d2e6d 2083 goto corrupt_etir;
07d6d2b8 2084 size = bfd_getl32 (ptr);
ab356be7
AM
2085 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2086 return FALSE;
07d6d2b8
AM
2087 if (rel1 != RELC_NONE)
2088 goto bad_context;
2089 while (op1-- > 0)
81699544
AM
2090 if (!image_write (abfd, ptr + 4, size))
2091 return FALSE;
07d6d2b8
AM
2092 }
2093 break;
2094
2095 /* Store global: write symbol value
2096 arg: cs global symbol name. */
2097 case ETIR__C_STO_GBL:
2098 _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
2099 if (h && h->sym)
2100 {
2101 if (h->sym->typ == EGSD__C_SYMG)
2102 {
96d3b80f
AM
2103 if (!alpha_vms_add_fixup_qr (info, abfd, h->sym->owner,
2104 h->sym->symbol_vector))
2105 return FALSE;
07d6d2b8
AM
2106 op1 = 0;
2107 }
2108 else
2109 {
2110 op1 = alpha_vms_get_sym_value (h->sym->section,
2111 h->sym->value);
96d3b80f
AM
2112 if (!alpha_vms_add_qw_reloc (info))
2113 return FALSE;
07d6d2b8
AM
2114 }
2115 }
81699544
AM
2116 if (!image_write_q (abfd, op1))
2117 return FALSE;
07d6d2b8
AM
2118 break;
2119
2120 /* Store code address: write address of entry point
2121 arg: cs global symbol name (procedure). */
2122 case ETIR__C_STO_CA:
2123 _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
2124 if (h && h->sym)
2125 {
2126 if (h->sym->flags & EGSY__V_NORM)
2127 {
2128 /* That's really a procedure. */
2129 if (h->sym->typ == EGSD__C_SYMG)
2130 {
96d3b80f
AM
2131 if (!alpha_vms_add_fixup_ca (info, abfd, h->sym->owner))
2132 return FALSE;
07d6d2b8
AM
2133 op1 = h->sym->symbol_vector;
2134 }
2135 else
2136 {
2137 op1 = alpha_vms_get_sym_value (h->sym->code_section,
2138 h->sym->code_value);
96d3b80f
AM
2139 if (!alpha_vms_add_qw_reloc (info))
2140 return FALSE;
07d6d2b8
AM
2141 }
2142 }
2143 else
2144 {
2145 /* Symbol is not a procedure. */
2146 abort ();
2147 }
2148 }
81699544
AM
2149 if (!image_write_q (abfd, op1))
2150 return FALSE;
07d6d2b8
AM
2151 break;
2152
2153 /* Store offset to psect: pop stack, add low 32 bits to base of psect
2154 arg: none. */
2155 case ETIR__C_STO_OFF:
ab356be7
AM
2156 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2157 return FALSE;
07d6d2b8
AM
2158
2159 if (!(rel1 & RELC_SEC_BASE))
2160 abort ();
2161
2162 op1 = alpha_vms_fix_sec_rel (abfd, info, rel1, op1);
2163 rel1 = RELC_REL;
81699544
AM
2164 if (!image_write_q (abfd, op1))
2165 return FALSE;
07d6d2b8
AM
2166 break;
2167
2168 /* Store immediate
2169 arg: lw count of bytes
2170 da data. */
2171 case ETIR__C_STO_IMM:
2172 {
2173 unsigned int size;
95e34ef7 2174
2c0e48e5 2175 if (ptr + 4 > maxptr)
c53d2e6d 2176 goto corrupt_etir;
07d6d2b8 2177 size = bfd_getl32 (ptr);
81699544
AM
2178 if (!image_write (abfd, ptr + 4, size))
2179 return FALSE;
07d6d2b8
AM
2180 }
2181 break;
2182
2183 /* This code is 'reserved to digital' according to the openVMS
2184 linker manual, however it is generated by the DEC C compiler
2185 and defined in the include file.
2186 FIXME, since the following is just a guess
2187 store global longword: store 32bit value of symbol
2188 arg: cs symbol name. */
2189 case ETIR__C_STO_GBL_LW:
2190 _bfd_vms_get_value (abfd, ptr, maxptr, info, &op1, &h);
95e34ef7 2191#if 0
07d6d2b8 2192 abort ();
95e34ef7 2193#endif
81699544
AM
2194 if (!image_write_l (abfd, op1))
2195 return FALSE;
07d6d2b8 2196 break;
95e34ef7 2197
07d6d2b8
AM
2198 case ETIR__C_STO_RB:
2199 case ETIR__C_STO_AB:
2200 case ETIR__C_STO_LP_PSB:
4eca0228
AM
2201 _bfd_error_handler (_("%s: not supported"),
2202 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2203 return FALSE;
2204 break;
2205 case ETIR__C_STO_HINT_GBL:
2206 case ETIR__C_STO_HINT_PS:
4eca0228
AM
2207 _bfd_error_handler (_("%s: not implemented"),
2208 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2209 return FALSE;
2210 break;
95e34ef7 2211
07d6d2b8
AM
2212 /* 200 Store-conditional Linkage Pair
2213 arg: none. */
2214 case ETIR__C_STC_LP:
95e34ef7 2215
07d6d2b8
AM
2216 /* 202 Store-conditional Address at global address
2217 lw linkage index
2218 cs global name. */
95e34ef7 2219
07d6d2b8 2220 case ETIR__C_STC_GBL:
95e34ef7 2221
07d6d2b8
AM
2222 /* 203 Store-conditional Code Address at global address
2223 lw linkage index
2224 cs procedure name. */
2225 case ETIR__C_STC_GCA:
95e34ef7 2226
07d6d2b8
AM
2227 /* 204 Store-conditional Address at psect + offset
2228 lw linkage index
2229 lw psect index
2230 qw offset. */
2231 case ETIR__C_STC_PS:
4eca0228
AM
2232 _bfd_error_handler (_("%s: not supported"),
2233 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2234 return FALSE;
2235 break;
2236
2237 /* 201 Store-conditional Linkage Pair with Procedure Signature
2238 lw linkage index
2239 cs procedure name
2240 by signature length
2241 da signature. */
2242
2243 case ETIR__C_STC_LP_PSB:
2244 _bfd_vms_get_value (abfd, ptr + 4, maxptr, info, &op1, &h);
2245 if (h && h->sym)
2246 {
2247 if (h->sym->typ == EGSD__C_SYMG)
2248 {
96d3b80f
AM
2249 if (!alpha_vms_add_fixup_lp (info, abfd, h->sym->owner))
2250 return FALSE;
07d6d2b8
AM
2251 op1 = h->sym->symbol_vector;
2252 op2 = 0;
2253 }
2254 else
2255 {
2256 op1 = alpha_vms_get_sym_value (h->sym->code_section,
2257 h->sym->code_value);
2258 op2 = alpha_vms_get_sym_value (h->sym->section,
2259 h->sym->value);
2260 }
2261 }
2262 else
2263 {
2264 /* Undefined symbol. */
2265 op1 = 0;
2266 op2 = 0;
2267 }
81699544
AM
2268 if (!image_write_q (abfd, op1)
2269 || !image_write_q (abfd, op2))
2270 return FALSE;
07d6d2b8
AM
2271 break;
2272
2273 /* 205 Store-conditional NOP at address of global
2274 arg: none. */
2275 case ETIR__C_STC_NOP_GBL:
2276 /* ALPHA_R_NOP */
2277
2278 /* 207 Store-conditional BSR at global address
2279 arg: none. */
2280
2281 case ETIR__C_STC_BSR_GBL:
2282 /* ALPHA_R_BSR */
2283
2284 /* 209 Store-conditional LDA at global address
2285 arg: none. */
2286
2287 case ETIR__C_STC_LDA_GBL:
2288 /* ALPHA_R_LDA */
2289
2290 /* 211 Store-conditional BSR or Hint at global address
2291 arg: none. */
2292
2293 case ETIR__C_STC_BOH_GBL:
2294 /* Currentl ignored. */
2295 break;
2296
2297 /* 213 Store-conditional NOP,BSR or HINT at global address
2298 arg: none. */
2299
2300 case ETIR__C_STC_NBH_GBL:
2301
2302 /* 206 Store-conditional NOP at pect + offset
2303 arg: none. */
2304
2305 case ETIR__C_STC_NOP_PS:
2306
2307 /* 208 Store-conditional BSR at pect + offset
2308 arg: none. */
2309
2310 case ETIR__C_STC_BSR_PS:
2311
2312 /* 210 Store-conditional LDA at psect + offset
2313 arg: none. */
2314
2315 case ETIR__C_STC_LDA_PS:
2316
2317 /* 212 Store-conditional BSR or Hint at pect + offset
2318 arg: none. */
2319
2320 case ETIR__C_STC_BOH_PS:
2321
2322 /* 214 Store-conditional NOP, BSR or HINT at psect + offset
2323 arg: none. */
2324 case ETIR__C_STC_NBH_PS:
695344c0 2325 _bfd_error_handler (_("%s: not supported"),
4eca0228 2326 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2327 return FALSE;
2328 break;
2329
2330 /* Det relocation base: pop stack, set image location counter
2331 arg: none. */
2332 case ETIR__C_CTL_SETRB:
ab356be7
AM
2333 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2334 return FALSE;
07d6d2b8
AM
2335 if (!(rel1 & RELC_SEC_BASE))
2336 abort ();
2337 image_set_ptr (abfd, op1, rel1 & RELC_MASK, info);
2338 break;
2339
2340 /* Augment relocation base: increment image location counter by offset
2341 arg: lw offset value. */
2342 case ETIR__C_CTL_AUGRB:
2c0e48e5 2343 if (ptr + 4 > maxptr)
c53d2e6d 2344 goto corrupt_etir;
07d6d2b8
AM
2345 op1 = bfd_getl32 (ptr);
2346 image_inc_ptr (abfd, op1);
2347 break;
2348
2349 /* Define location: pop index, save location counter under index
2350 arg: none. */
2351 case ETIR__C_CTL_DFLOC:
ab356be7
AM
2352 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2353 return FALSE;
07d6d2b8
AM
2354 if (rel1 != RELC_NONE)
2355 goto bad_context;
9cb56943
AM
2356 if (!dst_define_location (abfd, op1))
2357 return FALSE;
07d6d2b8
AM
2358 break;
2359
2360 /* Set location: pop index, restore location counter from index
2361 arg: none. */
2362 case ETIR__C_CTL_STLOC:
ab356be7
AM
2363 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2364 return FALSE;
07d6d2b8
AM
2365 if (rel1 != RELC_NONE)
2366 goto bad_context;
7bac4137
AM
2367 if (!dst_restore_location (abfd, op1))
2368 {
2369 bfd_set_error (bfd_error_bad_value);
2370 _bfd_error_handler (_("invalid %s"), "ETIR__C_CTL_STLOC");
2371 return FALSE;
2372 }
07d6d2b8
AM
2373 break;
2374
2375 /* Stack defined location: pop index, push location counter from index
2376 arg: none. */
2377 case ETIR__C_CTL_STKDL:
ab356be7
AM
2378 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2379 return FALSE;
07d6d2b8
AM
2380 if (rel1 != RELC_NONE)
2381 goto bad_context;
7bac4137
AM
2382 if (!dst_retrieve_location (abfd, &op1))
2383 {
2384 bfd_set_error (bfd_error_bad_value);
2385 _bfd_error_handler (_("invalid %s"), "ETIR__C_CTL_STKDL");
2386 return FALSE;
2387 }
2388 if (!_bfd_vms_push (abfd, op1, RELC_NONE))
ab356be7 2389 return FALSE;
07d6d2b8
AM
2390 break;
2391
2392 case ETIR__C_OPR_NOP: /* No-op. */
2393 break;
2394
2395 case ETIR__C_OPR_ADD: /* Add. */
ab356be7
AM
2396 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2397 || !_bfd_vms_pop (abfd, &op2, &rel2))
2398 return FALSE;
07d6d2b8
AM
2399 if (rel1 == RELC_NONE && rel2 != RELC_NONE)
2400 rel1 = rel2;
2401 else if (rel1 != RELC_NONE && rel2 != RELC_NONE)
2402 goto bad_context;
ab356be7
AM
2403 if (!_bfd_vms_push (abfd, op1 + op2, rel1))
2404 return FALSE;
07d6d2b8
AM
2405 break;
2406
2407 case ETIR__C_OPR_SUB: /* Subtract. */
ab356be7
AM
2408 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2409 || !_bfd_vms_pop (abfd, &op2, &rel2))
2410 return FALSE;
07d6d2b8
AM
2411 if (rel1 == RELC_NONE && rel2 != RELC_NONE)
2412 rel1 = rel2;
2413 else if ((rel1 & RELC_SEC_BASE) && (rel2 & RELC_SEC_BASE))
2414 {
2415 op1 = alpha_vms_fix_sec_rel (abfd, info, rel1, op1);
2416 op2 = alpha_vms_fix_sec_rel (abfd, info, rel2, op2);
2417 rel1 = RELC_NONE;
2418 }
2419 else if (rel1 != RELC_NONE && rel2 != RELC_NONE)
2420 goto bad_context;
ab356be7
AM
2421 if (!_bfd_vms_push (abfd, op2 - op1, rel1))
2422 return FALSE;
07d6d2b8
AM
2423 break;
2424
2425 case ETIR__C_OPR_MUL: /* Multiply. */
ab356be7
AM
2426 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2427 || !_bfd_vms_pop (abfd, &op2, &rel2))
2428 return FALSE;
07d6d2b8
AM
2429 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2430 goto bad_context;
ab356be7
AM
2431 if (!_bfd_vms_push (abfd, op1 * op2, RELC_NONE))
2432 return FALSE;
07d6d2b8
AM
2433 break;
2434
2435 case ETIR__C_OPR_DIV: /* Divide. */
ab356be7
AM
2436 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2437 || !_bfd_vms_pop (abfd, &op2, &rel2))
2438 return FALSE;
07d6d2b8
AM
2439 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2440 goto bad_context;
2441 if (op2 == 0)
ab356be7
AM
2442 {
2443 if (!_bfd_vms_push (abfd, 0, RELC_NONE))
2444 return FALSE;
2445 }
07d6d2b8 2446 else
ab356be7
AM
2447 {
2448 if (!_bfd_vms_push (abfd, op2 / op1, RELC_NONE))
2449 return FALSE;
2450 }
07d6d2b8
AM
2451 break;
2452
2453 case ETIR__C_OPR_AND: /* Logical AND. */
ab356be7
AM
2454 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2455 || !_bfd_vms_pop (abfd, &op2, &rel2))
2456 return FALSE;
07d6d2b8
AM
2457 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2458 goto bad_context;
ab356be7
AM
2459 if (!_bfd_vms_push (abfd, op1 & op2, RELC_NONE))
2460 return FALSE;
07d6d2b8
AM
2461 break;
2462
2463 case ETIR__C_OPR_IOR: /* Logical inclusive OR. */
ab356be7
AM
2464 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2465 || !_bfd_vms_pop (abfd, &op2, &rel2))
2466 return FALSE;
07d6d2b8
AM
2467 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2468 goto bad_context;
ab356be7
AM
2469 if (!_bfd_vms_push (abfd, op1 | op2, RELC_NONE))
2470 return FALSE;
07d6d2b8
AM
2471 break;
2472
2473 case ETIR__C_OPR_EOR: /* Logical exclusive OR. */
ab356be7
AM
2474 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2475 || !_bfd_vms_pop (abfd, &op2, &rel2))
2476 return FALSE;
07d6d2b8
AM
2477 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2478 goto bad_context;
ab356be7
AM
2479 if (!_bfd_vms_push (abfd, op1 ^ op2, RELC_NONE))
2480 return FALSE;
07d6d2b8
AM
2481 break;
2482
2483 case ETIR__C_OPR_NEG: /* Negate. */
ab356be7
AM
2484 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2485 return FALSE;
07d6d2b8
AM
2486 if (rel1 != RELC_NONE)
2487 goto bad_context;
ab356be7
AM
2488 if (!_bfd_vms_push (abfd, -op1, RELC_NONE))
2489 return FALSE;
07d6d2b8
AM
2490 break;
2491
2492 case ETIR__C_OPR_COM: /* Complement. */
ab356be7
AM
2493 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2494 return FALSE;
07d6d2b8
AM
2495 if (rel1 != RELC_NONE)
2496 goto bad_context;
ab356be7
AM
2497 if (!_bfd_vms_push (abfd, ~op1, RELC_NONE))
2498 return FALSE;
07d6d2b8
AM
2499 break;
2500
2501 case ETIR__C_OPR_ASH: /* Arithmetic shift. */
ab356be7
AM
2502 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2503 || !_bfd_vms_pop (abfd, &op2, &rel2))
2504 return FALSE;
07d6d2b8
AM
2505 if (rel1 != RELC_NONE || rel2 != RELC_NONE)
2506 {
2507 bad_context:
4eca0228
AM
2508 _bfd_error_handler (_("invalid use of %s with contexts"),
2509 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2510 return FALSE;
2511 }
2512 if ((int)op2 < 0) /* Shift right. */
2513 op1 >>= -(int)op2;
2514 else /* Shift left. */
2515 op1 <<= (int)op2;
ab356be7
AM
2516 if (!_bfd_vms_push (abfd, op1, RELC_NONE)) /* FIXME: sym. */
2517 return FALSE;
07d6d2b8
AM
2518 break;
2519
2520 case ETIR__C_OPR_INSV: /* Insert field. */
2521 case ETIR__C_OPR_USH: /* Unsigned shift. */
2522 case ETIR__C_OPR_ROT: /* Rotate. */
2523 case ETIR__C_OPR_REDEF: /* Redefine symbol to current location. */
2524 case ETIR__C_OPR_DFLIT: /* Define a literal. */
4eca0228
AM
2525 _bfd_error_handler (_("%s: not supported"),
2526 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
2527 return FALSE;
2528 break;
2529
2530 case ETIR__C_OPR_SEL: /* Select. */
ab356be7
AM
2531 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2532 return FALSE;
07d6d2b8 2533 if (op1 & 0x01L)
ab356be7
AM
2534 {
2535 if (!_bfd_vms_pop (abfd, &op1, &rel1))
2536 return FALSE;
2537 }
07d6d2b8
AM
2538 else
2539 {
ab356be7
AM
2540 if (!_bfd_vms_pop (abfd, &op1, &rel1)
2541 || !_bfd_vms_pop (abfd, &op2, &rel2))
2542 return FALSE;
2543 if (!_bfd_vms_push (abfd, op1, rel1))
2544 return FALSE;
07d6d2b8
AM
2545 }
2546 break;
2547
2548 default:
4eca0228 2549 _bfd_error_handler (_("reserved cmd %d"), cmd);
07d6d2b8
AM
2550 return FALSE;
2551 break;
2552 }
95e34ef7
TG
2553
2554 ptr += cmd_length - 4;
2555 }
2556
2557 return TRUE;
2558}
2559
2560/* Process EDBG/ETBT record.
2561 Return TRUE on success, FALSE on error */
2562
2563static bfd_boolean
2564vms_slurp_debug (bfd *abfd)
2565{
2566 asection *section = PRIV (dst_section);
2567
2568 if (section == NULL)
2569 {
2570 /* We have no way to find out beforehand how much debug info there
2571 is in an object file, so pick an initial amount and grow it as
2572 needed later. */
2573 flagword flags = SEC_HAS_CONTENTS | SEC_DEBUGGING | SEC_RELOC
07d6d2b8 2574 | SEC_IN_MEMORY;
95e34ef7
TG
2575
2576 section = bfd_make_section (abfd, "$DST$");
2577 if (!section)
2578 return FALSE;
fd361982 2579 if (!bfd_set_section_flags (section, flags))
95e34ef7
TG
2580 return FALSE;
2581 PRIV (dst_section) = section;
2582 }
2583
2584 PRIV (image_section) = section;
2585 PRIV (image_offset) = section->size;
95e34ef7
TG
2586
2587 if (!_bfd_vms_slurp_etir (abfd, NULL))
2588 return FALSE;
2589
44273c5b 2590 section->size = PRIV (image_offset);
95e34ef7
TG
2591 return TRUE;
2592}
2593
2594/* Process EDBG record.
2595 Return TRUE on success, FALSE on error. */
2596
2597static bfd_boolean
2598_bfd_vms_slurp_edbg (bfd *abfd)
2599{
2600 vms_debug2 ((2, "EDBG\n"));
2601
44273c5b 2602 abfd->flags |= HAS_DEBUG | HAS_LINENO;
95e34ef7
TG
2603
2604 return vms_slurp_debug (abfd);
2605}
2606
2607/* Process ETBT record.
2608 Return TRUE on success, FALSE on error. */
2609
2610static bfd_boolean
2611_bfd_vms_slurp_etbt (bfd *abfd)
2612{
2613 vms_debug2 ((2, "ETBT\n"));
2614
2615 abfd->flags |= HAS_LINENO;
2616
2617 return vms_slurp_debug (abfd);
2618}
2619
2620/* Process EEOM record.
2621 Return TRUE on success, FALSE on error. */
2622
2623static bfd_boolean
2624_bfd_vms_slurp_eeom (bfd *abfd)
2625{
2626 struct vms_eeom *eeom = (struct vms_eeom *) PRIV (recrd.rec);
2627
2628 vms_debug2 ((2, "EEOM\n"));
2629
ca4cf9b9
NC
2630 /* PR 21813: Check for an undersized record. */
2631 if (PRIV (recrd.buf_size) < sizeof (* eeom))
2632 {
38f14ab8 2633 _bfd_error_handler (_("corrupt EEOM record - size is too small"));
ca4cf9b9
NC
2634 bfd_set_error (bfd_error_bad_value);
2635 return FALSE;
2636 }
2637
95e34ef7
TG
2638 PRIV (eom_data).eom_l_total_lps = bfd_getl32 (eeom->total_lps);
2639 PRIV (eom_data).eom_w_comcod = bfd_getl16 (eeom->comcod);
2640 if (PRIV (eom_data).eom_w_comcod > 1)
2641 {
38f14ab8 2642 _bfd_error_handler (_("object module not error-free !"));
95e34ef7
TG
2643 bfd_set_error (bfd_error_bad_value);
2644 return FALSE;
2645 }
2646
2647 PRIV (eom_data).eom_has_transfer = FALSE;
2648 if (PRIV (recrd.rec_size) > 10)
2649 {
2650 PRIV (eom_data).eom_has_transfer = TRUE;
2651 PRIV (eom_data).eom_b_tfrflg = eeom->tfrflg;
2652 PRIV (eom_data).eom_l_psindx = bfd_getl32 (eeom->psindx);
2653 PRIV (eom_data).eom_l_tfradr = bfd_getl32 (eeom->tfradr);
2654
2655 abfd->start_address = PRIV (eom_data).eom_l_tfradr;
2656 }
2657 return TRUE;
2658}
2659
2660/* Slurp an ordered set of VMS object records. Return FALSE on error. */
2661
2662static bfd_boolean
2663_bfd_vms_slurp_object_records (bfd * abfd)
2664{
f75fbe8a 2665 bfd_boolean ok;
44273c5b 2666 int type;
95e34ef7
TG
2667
2668 do
2669 {
2670 vms_debug2 ((7, "reading at %08lx\n", (unsigned long)bfd_tell (abfd)));
2671
44273c5b
TG
2672 type = _bfd_vms_get_object_record (abfd);
2673 if (type < 0)
95e34ef7
TG
2674 {
2675 vms_debug2 ((2, "next_record failed\n"));
2676 return FALSE;
2677 }
2678
95e34ef7
TG
2679 switch (type)
2680 {
07d6d2b8 2681 case EOBJ__C_EMH:
f75fbe8a 2682 ok = _bfd_vms_slurp_ehdr (abfd);
07d6d2b8
AM
2683 break;
2684 case EOBJ__C_EEOM:
f75fbe8a 2685 ok = _bfd_vms_slurp_eeom (abfd);
07d6d2b8
AM
2686 break;
2687 case EOBJ__C_EGSD:
f75fbe8a 2688 ok = _bfd_vms_slurp_egsd (abfd);
07d6d2b8
AM
2689 break;
2690 case EOBJ__C_ETIR:
f75fbe8a 2691 ok = TRUE; /* _bfd_vms_slurp_etir (abfd); */
07d6d2b8
AM
2692 break;
2693 case EOBJ__C_EDBG:
f75fbe8a 2694 ok = _bfd_vms_slurp_edbg (abfd);
07d6d2b8
AM
2695 break;
2696 case EOBJ__C_ETBT:
f75fbe8a 2697 ok = _bfd_vms_slurp_etbt (abfd);
07d6d2b8
AM
2698 break;
2699 default:
f75fbe8a 2700 ok = FALSE;
95e34ef7 2701 }
f75fbe8a 2702 if (!ok)
95e34ef7
TG
2703 {
2704 vms_debug2 ((2, "slurp type %d failed\n", type));
2705 return FALSE;
2706 }
2707 }
2708 while (type != EOBJ__C_EEOM);
2709
2710 return TRUE;
2711}
2712
2713/* Initialize private data */
2714static bfd_boolean
2715vms_initialize (bfd * abfd)
2716{
986f0783 2717 size_t amt;
95e34ef7
TG
2718
2719 amt = sizeof (struct vms_private_data_struct);
2720 abfd->tdata.any = bfd_zalloc (abfd, amt);
2721 if (abfd->tdata.any == NULL)
2722 return FALSE;
2723
2724 PRIV (recrd.file_format) = FF_UNKNOWN;
2725
2726 amt = sizeof (struct stack_struct) * STACKSIZE;
2727 PRIV (stack) = bfd_alloc (abfd, amt);
2728 if (PRIV (stack) == NULL)
2729 goto error_ret1;
2730
2731 return TRUE;
2732
2733 error_ret1:
2734 bfd_release (abfd, abfd->tdata.any);
2735 abfd->tdata.any = NULL;
2736 return FALSE;
2737}
2738
a7ac9aa5
AM
2739/* Free malloc'd memory. */
2740
2741static void
2742alpha_vms_free_private (bfd *abfd)
2743{
2744 struct module *module;
2745
2746 free (PRIV (recrd.buf));
2747 free (PRIV (sections));
2748 free (PRIV (syms));
2749 free (PRIV (dst_ptr_offsets));
2750
2751 for (module = PRIV (modules); module; module = module->next)
2752 free (module->file_table);
2753}
2754
95e34ef7
TG
2755/* Check the format for a file being read.
2756 Return a (bfd_target *) if it's an object file or zero if not. */
2757
cb001c0d 2758static bfd_cleanup
95e34ef7
TG
2759alpha_vms_object_p (bfd *abfd)
2760{
8185f55c 2761 void *tdata_save = abfd->tdata.any;
95e34ef7
TG
2762 unsigned int test_len;
2763 unsigned char *buf;
2764
2765 vms_debug2 ((1, "vms_object_p(%p)\n", abfd));
2766
2767 /* Allocate alpha-vms specific data. */
2768 if (!vms_initialize (abfd))
a7ac9aa5
AM
2769 {
2770 abfd->tdata.any = tdata_save;
2771 return NULL;
2772 }
95e34ef7
TG
2773
2774 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET))
1b088c82 2775 goto error_ret;
95e34ef7
TG
2776
2777 /* The first challenge with VMS is to discover the kind of the file.
2778
2779 Image files (executable or shared images) are stored as a raw
2780 stream of bytes (like on UNIX), but there is no magic number.
2781
2782 Object files are written with RMS (record management service), ie
2783 each records are preceeded by its length (on a word - 2 bytes), and
2784 padded for word-alignment. That would be simple but when files
2785 are transfered to a UNIX filesystem (using ftp), records are lost.
2786 Only the raw content of the records are transfered. Fortunately,
2787 the Alpha Object file format also store the length of the record
2788 in the records. Is that clear ? */
2789
2790 /* Minimum is 6 bytes for objects (2 bytes size, 2 bytes record id,
2791 2 bytes size repeated) and 12 bytes for images (4 bytes major id,
2792 4 bytes minor id, 4 bytes length). */
2793 test_len = 12;
1b088c82 2794 buf = _bfd_malloc_and_read (abfd, test_len, test_len);
95e34ef7
TG
2795 if (buf == NULL)
2796 goto error_ret;
2797 PRIV (recrd.buf) = buf;
2798 PRIV (recrd.buf_size) = test_len;
95e34ef7
TG
2799 PRIV (recrd.rec) = buf;
2800
95e34ef7
TG
2801 /* Is it an image? */
2802 if ((bfd_getl32 (buf) == EIHD__K_MAJORID)
2803 && (bfd_getl32 (buf + 4) == EIHD__K_MINORID))
2804 {
95e34ef7
TG
2805 unsigned int eisd_offset, eihs_offset;
2806
2807 /* Extract the header size. */
2808 PRIV (recrd.rec_size) = bfd_getl32 (buf + EIHD__L_SIZE);
2809
af47dcbf
TG
2810 /* The header size is 0 for DSF files. */
2811 if (PRIV (recrd.rec_size) == 0)
07d6d2b8 2812 PRIV (recrd.rec_size) = sizeof (struct vms_eihd);
af47dcbf 2813
8a2df5e2 2814 /* PR 21813: Check for a truncated record. */
1b088c82
AM
2815 /* PR 17512: file: 7d7c57c2. */
2816 if (PRIV (recrd.rec_size) < sizeof (struct vms_eihd))
2817 goto err_wrong_format;
95e34ef7 2818
1b088c82
AM
2819 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET))
2820 goto error_ret;
95e34ef7 2821
1b088c82
AM
2822 free (PRIV (recrd.buf));
2823 PRIV (recrd.buf) = NULL;
2824 buf = _bfd_malloc_and_read (abfd, PRIV (recrd.rec_size),
2825 PRIV (recrd.rec_size));
2826 if (buf == NULL)
2827 goto error_ret;
95e34ef7 2828
1b088c82
AM
2829 PRIV (recrd.buf) = buf;
2830 PRIV (recrd.buf_size) = PRIV (recrd.rec_size);
95e34ef7
TG
2831 PRIV (recrd.rec) = buf;
2832
2833 vms_debug2 ((2, "file type is image\n"));
2834
535b785f 2835 if (!_bfd_vms_slurp_eihd (abfd, &eisd_offset, &eihs_offset))
07d6d2b8 2836 goto err_wrong_format;
95e34ef7 2837
535b785f 2838 if (!_bfd_vms_slurp_eisd (abfd, eisd_offset))
07d6d2b8 2839 goto err_wrong_format;
95e34ef7
TG
2840
2841 /* EIHS is optional. */
535b785f 2842 if (eihs_offset != 0 && !_bfd_vms_slurp_eihs (abfd, eihs_offset))
07d6d2b8 2843 goto err_wrong_format;
95e34ef7
TG
2844 }
2845 else
2846 {
2847 int type;
2848
2849 /* Assume it's a module and adjust record pointer if necessary. */
2850 maybe_adjust_record_pointer_for_object (abfd);
2851
2852 /* But is it really a module? */
2853 if (bfd_getl16 (PRIV (recrd.rec)) <= EOBJ__C_MAXRECTYP
07d6d2b8
AM
2854 && bfd_getl16 (PRIV (recrd.rec) + 2) <= EOBJ__C_MAXRECSIZ)
2855 {
2856 if (vms_get_remaining_object_record (abfd, test_len) <= 0)
2857 goto err_wrong_format;
95e34ef7 2858
07d6d2b8 2859 vms_debug2 ((2, "file type is module\n"));
95e34ef7 2860
07d6d2b8
AM
2861 type = bfd_getl16 (PRIV (recrd.rec));
2862 if (type != EOBJ__C_EMH || !_bfd_vms_slurp_ehdr (abfd))
2863 goto err_wrong_format;
95e34ef7 2864
07d6d2b8
AM
2865 if (!_bfd_vms_slurp_object_records (abfd))
2866 goto err_wrong_format;
2867 }
95e34ef7 2868 else
07d6d2b8 2869 goto err_wrong_format;
95e34ef7
TG
2870 }
2871
2872 /* Set arch_info to alpha. */
2873
2874 if (! bfd_default_set_arch_mach (abfd, bfd_arch_alpha, 0))
2875 goto err_wrong_format;
2876
cb001c0d 2877 return alpha_vms_free_private;
95e34ef7
TG
2878
2879 err_wrong_format:
2880 bfd_set_error (bfd_error_wrong_format);
2881
2882 error_ret:
a7ac9aa5 2883 alpha_vms_free_private (abfd);
95e34ef7
TG
2884 if (abfd->tdata.any != tdata_save && abfd->tdata.any != NULL)
2885 bfd_release (abfd, abfd->tdata.any);
2886 abfd->tdata.any = tdata_save;
2887 return NULL;
2888}
2889\f
2890/* Image write. */
2891
bd7b51b4
TG
2892/* Write an EMH/MHD record. */
2893
2894static void
2895_bfd_vms_write_emh (bfd *abfd)
2896{
2897 struct vms_rec_wr *recwr = &PRIV (recwr);
2898
2899 _bfd_vms_output_alignment (recwr, 2);
2900
2901 /* EMH. */
2902 _bfd_vms_output_begin (recwr, EOBJ__C_EMH);
2903 _bfd_vms_output_short (recwr, EMH__C_MHD);
2904 _bfd_vms_output_short (recwr, EOBJ__C_STRLVL);
2905 _bfd_vms_output_long (recwr, 0);
2906 _bfd_vms_output_long (recwr, 0);
2907 _bfd_vms_output_long (recwr, MAX_OUTREC_SIZE);
2908
2909 /* Create module name from filename. */
2910 if (bfd_get_filename (abfd) != 0)
2911 {
2912 char *module = vms_get_module_name (bfd_get_filename (abfd), TRUE);
2913 _bfd_vms_output_counted (recwr, module);
2914 free (module);
2915 }
2916 else
2917 _bfd_vms_output_counted (recwr, "NONAME");
2918
2919 _bfd_vms_output_counted (recwr, BFD_VERSION_STRING);
2920 _bfd_vms_output_dump (recwr, get_vms_time_string (), EMH_DATE_LENGTH);
2921 _bfd_vms_output_fill (recwr, 0, EMH_DATE_LENGTH);
2922 _bfd_vms_output_end (abfd, recwr);
2923}
2924
2925/* Write an EMH/LMN record. */
2926
2927static void
2928_bfd_vms_write_lmn (bfd *abfd, const char *name)
2929{
2930 char version [64];
2931 struct vms_rec_wr *recwr = &PRIV (recwr);
2932 unsigned int ver = BFD_VERSION / 10000;
2933
2934 /* LMN. */
2935 _bfd_vms_output_begin (recwr, EOBJ__C_EMH);
2936 _bfd_vms_output_short (recwr, EMH__C_LNM);
2937 snprintf (version, sizeof (version), "%s %d.%d.%d", name,
07d6d2b8 2938 ver / 10000, (ver / 100) % 100, ver % 100);
bd7b51b4
TG
2939 _bfd_vms_output_dump (recwr, (unsigned char *)version, strlen (version));
2940 _bfd_vms_output_end (abfd, recwr);
2941}
2942
2943
2944/* Write eom record for bfd abfd. Return FALSE on error. */
2945
2946static bfd_boolean
2947_bfd_vms_write_eeom (bfd *abfd)
2948{
2949 struct vms_rec_wr *recwr = &PRIV (recwr);
2950
2951 vms_debug2 ((2, "vms_write_eeom\n"));
2952
2953 _bfd_vms_output_alignment (recwr, 2);
2954
2955 _bfd_vms_output_begin (recwr, EOBJ__C_EEOM);
f1bb0388 2956 _bfd_vms_output_long (recwr, PRIV (vms_linkage_index + 1) >> 1);
bd7b51b4
TG
2957 _bfd_vms_output_byte (recwr, 0); /* Completion code. */
2958 _bfd_vms_output_byte (recwr, 0); /* Fill byte. */
2959
2960 if ((abfd->flags & EXEC_P) == 0
2961 && bfd_get_start_address (abfd) != (bfd_vma)-1)
2962 {
2963 asection *section;
2964
2965 section = bfd_get_section_by_name (abfd, ".link");
2966 if (section == 0)
2967 {
2968 bfd_set_error (bfd_error_nonrepresentable_section);
2969 return FALSE;
2970 }
2971 _bfd_vms_output_short (recwr, 0);
1b3d1dbf 2972 _bfd_vms_output_long (recwr, (unsigned long) section->target_index);
bd7b51b4
TG
2973 _bfd_vms_output_long (recwr,
2974 (unsigned long) bfd_get_start_address (abfd));
2975 _bfd_vms_output_long (recwr, 0);
2976 }
2977
2978 _bfd_vms_output_end (abfd, recwr);
2979 return TRUE;
2980}
2981
96d3b80f 2982static void *
95e34ef7
TG
2983vector_grow1 (struct vector_type *vec, size_t elsz)
2984{
96d3b80f 2985 if (vec->nbr_el >= vec->max_el)
95e34ef7 2986 {
96d3b80f
AM
2987 if (vec->max_el == 0)
2988 {
2989 vec->max_el = 16;
1f4361a7 2990 vec->els = bfd_malloc (vec->max_el * elsz);
96d3b80f
AM
2991 }
2992 else
2993 {
1f4361a7 2994 size_t amt;
96d3b80f
AM
2995 if (vec->max_el > -1u / 2)
2996 {
2997 bfd_set_error (bfd_error_file_too_big);
2998 return NULL;
2999 }
3000 vec->max_el *= 2;
1f4361a7
AM
3001 if (_bfd_mul_overflow (vec->max_el, elsz, &amt))
3002 {
3003 bfd_set_error (bfd_error_file_too_big);
3004 return NULL;
3005 }
9cb56943 3006 vec->els = bfd_realloc_or_free (vec->els, amt);
96d3b80f 3007 }
95e34ef7 3008 }
96d3b80f
AM
3009 if (vec->els == NULL)
3010 return NULL;
3011 return (char *) vec->els + elsz * vec->nbr_el++;
95e34ef7
TG
3012}
3013
3014/* Bump ABFD file position to next block. */
3015
3016static void
3017alpha_vms_file_position_block (bfd *abfd)
3018{
3019 /* Next block. */
3020 PRIV (file_pos) += VMS_BLOCK_SIZE - 1;
3021 PRIV (file_pos) -= (PRIV (file_pos) % VMS_BLOCK_SIZE);
3022}
3023
44273c5b
TG
3024/* Convert from internal structure SRC to external structure DST. */
3025
95e34ef7
TG
3026static void
3027alpha_vms_swap_eisd_out (struct vms_internal_eisd_map *src,
07d6d2b8 3028 struct vms_eisd *dst)
95e34ef7
TG
3029{
3030 bfd_putl32 (src->u.eisd.majorid, dst->majorid);
3031 bfd_putl32 (src->u.eisd.minorid, dst->minorid);
3032 bfd_putl32 (src->u.eisd.eisdsize, dst->eisdsize);
3033 if (src->u.eisd.eisdsize <= EISD__K_LENEND)
3034 return;
3035 bfd_putl32 (src->u.eisd.secsize, dst->secsize);
3036 bfd_putl64 (src->u.eisd.virt_addr, dst->virt_addr);
3037 bfd_putl32 (src->u.eisd.flags, dst->flags);
3038 bfd_putl32 (src->u.eisd.vbn, dst->vbn);
3039 dst->pfc = src->u.eisd.pfc;
3040 dst->matchctl = src->u.eisd.matchctl;
3041 dst->type = src->u.eisd.type;
3042 dst->fill_1 = 0;
3043 if (src->u.eisd.flags & EISD__M_GBL)
3044 {
3045 bfd_putl32 (src->u.gbl_eisd.ident, dst->ident);
3046 memcpy (dst->gblnam, src->u.gbl_eisd.gblnam,
07d6d2b8 3047 src->u.gbl_eisd.gblnam[0] + 1);
95e34ef7
TG
3048 }
3049}
3050
3051/* Append EISD to the list of extra eisd for ABFD. */
3052
3053static void
3054alpha_vms_append_extra_eisd (bfd *abfd, struct vms_internal_eisd_map *eisd)
3055{
3056 eisd->next = NULL;
3057 if (PRIV (gbl_eisd_head) == NULL)
3058 PRIV (gbl_eisd_head) = eisd;
3059 else
3060 PRIV (gbl_eisd_tail)->next = eisd;
3061 PRIV (gbl_eisd_tail) = eisd;
3062}
3063
44273c5b
TG
3064/* Create an EISD for shared image SHRIMG.
3065 Return FALSE in case of error. */
3066
95e34ef7
TG
3067static bfd_boolean
3068alpha_vms_create_eisd_for_shared (bfd *abfd, bfd *shrimg)
3069{
3070 struct vms_internal_eisd_map *eisd;
3071 int namlen;
3072
3073 namlen = strlen (PRIV2 (shrimg, hdr_data.hdr_t_name));
3074 if (namlen + 5 > EISD__K_GBLNAMLEN)
3075 {
3076 /* Won't fit. */
3077 return FALSE;
3078 }
3079
3080 eisd = bfd_alloc (abfd, sizeof (*eisd));
3081 if (eisd == NULL)
3082 return FALSE;
3083
3084 /* Fill the fields. */
3085 eisd->u.gbl_eisd.common.majorid = EISD__K_MAJORID;
3086 eisd->u.gbl_eisd.common.minorid = EISD__K_MINORID;
3087 eisd->u.gbl_eisd.common.eisdsize = (EISD__K_LEN + 4 + namlen + 5 + 3) & ~3;
3088 eisd->u.gbl_eisd.common.secsize = VMS_BLOCK_SIZE; /* Must not be 0. */
3089 eisd->u.gbl_eisd.common.virt_addr = 0;
3090 eisd->u.gbl_eisd.common.flags = EISD__M_GBL;
3091 eisd->u.gbl_eisd.common.vbn = 0;
3092 eisd->u.gbl_eisd.common.pfc = 0;
3093 eisd->u.gbl_eisd.common.matchctl = PRIV2 (shrimg, matchctl);
3094 eisd->u.gbl_eisd.common.type = EISD__K_SHRPIC;
3095
3096 eisd->u.gbl_eisd.ident = PRIV2 (shrimg, ident);
3097 eisd->u.gbl_eisd.gblnam[0] = namlen + 4;
3098 memcpy (eisd->u.gbl_eisd.gblnam + 1, PRIV2 (shrimg, hdr_data.hdr_t_name),
07d6d2b8 3099 namlen);
95e34ef7
TG
3100 memcpy (eisd->u.gbl_eisd.gblnam + 1 + namlen, "_001", 4);
3101
3102 /* Append it to the list. */
3103 alpha_vms_append_extra_eisd (abfd, eisd);
3104
3105 return TRUE;
3106}
3107
44273c5b
TG
3108/* Create an EISD for section SEC.
3109 Return FALSE in case of failure. */
3110
95e34ef7
TG
3111static bfd_boolean
3112alpha_vms_create_eisd_for_section (bfd *abfd, asection *sec)
3113{
3114 struct vms_internal_eisd_map *eisd;
3115
3116 /* Only for allocating section. */
3117 if (!(sec->flags & SEC_ALLOC))
3118 return TRUE;
3119
3120 BFD_ASSERT (vms_section_data (sec)->eisd == NULL);
3121 eisd = bfd_alloc (abfd, sizeof (*eisd));
3122 if (eisd == NULL)
3123 return FALSE;
3124 vms_section_data (sec)->eisd = eisd;
3125
3126 /* Fill the fields. */
3127 eisd->u.eisd.majorid = EISD__K_MAJORID;
3128 eisd->u.eisd.minorid = EISD__K_MINORID;
3129 eisd->u.eisd.eisdsize = EISD__K_LEN;
3130 eisd->u.eisd.secsize =
3131 (sec->size + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1);
3132 eisd->u.eisd.virt_addr = sec->vma;
3133 eisd->u.eisd.flags = 0;
3134 eisd->u.eisd.vbn = 0; /* To be later defined. */
3135 eisd->u.eisd.pfc = 0; /* Default. */
3136 eisd->u.eisd.matchctl = EISD__K_MATALL;
3137 eisd->u.eisd.type = EISD__K_NORMAL;
3138
3139 if (sec->flags & SEC_CODE)
3140 eisd->u.eisd.flags |= EISD__M_EXE;
cf6b8767 3141 if (!(sec->flags & SEC_READONLY))
95e34ef7
TG
3142 eisd->u.eisd.flags |= EISD__M_WRT | EISD__M_CRF;
3143
5f101a3d
TG
3144 /* If relocations or fixup will be applied, make this isect writeable. */
3145 if (sec->flags & SEC_RELOC)
3146 eisd->u.eisd.flags |= EISD__M_WRT | EISD__M_CRF;
3147
8185f55c 3148 if (!(sec->flags & SEC_HAS_CONTENTS))
95e34ef7
TG
3149 {
3150 eisd->u.eisd.flags |= EISD__M_DZRO;
3151 eisd->u.eisd.flags &= ~EISD__M_CRF;
3152 }
3153 if (sec->flags & SEC_LINKER_CREATED)
3154 {
3155 if (strcmp (sec->name, "$FIXUP$") == 0)
07d6d2b8 3156 eisd->u.eisd.flags |= EISD__M_FIXUPVEC;
95e34ef7
TG
3157 }
3158
3159 /* Append it to the list. */
3160 eisd->next = NULL;
3161 if (PRIV (eisd_head) == NULL)
3162 PRIV (eisd_head) = eisd;
3163 else
3164 PRIV (eisd_tail)->next = eisd;
3165 PRIV (eisd_tail) = eisd;
3166
3167 return TRUE;
3168}
3169
44273c5b
TG
3170/* Layout executable ABFD and write it to the disk.
3171 Return FALSE in case of failure. */
3172
95e34ef7
TG
3173static bfd_boolean
3174alpha_vms_write_exec (bfd *abfd)
3175{
3176 struct vms_eihd eihd;
3177 struct vms_eiha *eiha;
3178 struct vms_eihi *eihi;
3179 struct vms_eihs *eihs = NULL;
3180 asection *sec;
3181 struct vms_internal_eisd_map *first_eisd;
3182 struct vms_internal_eisd_map *eisd;
3183 asection *dst;
44273c5b 3184 asection *dmt;
f9eeb9c9
TG
3185 file_ptr gst_filepos = 0;
3186 unsigned int lnkflags = 0;
95e34ef7 3187
44273c5b 3188 /* Build the EIHD. */
95e34ef7
TG
3189 PRIV (file_pos) = EIHD__C_LENGTH;
3190
3191 memset (&eihd, 0, sizeof (eihd));
3192 memset (eihd.fill_2, 0xff, sizeof (eihd.fill_2));
3193
3194 bfd_putl32 (EIHD__K_MAJORID, eihd.majorid);
3195 bfd_putl32 (EIHD__K_MINORID, eihd.minorid);
3196
3197 bfd_putl32 (sizeof (eihd), eihd.size);
3198 bfd_putl32 (0, eihd.isdoff);
3199 bfd_putl32 (0, eihd.activoff);
3200 bfd_putl32 (0, eihd.symdbgoff);
3201 bfd_putl32 (0, eihd.imgidoff);
3202 bfd_putl32 (0, eihd.patchoff);
3203 bfd_putl64 (0, eihd.iafva);
3204 bfd_putl32 (0, eihd.version_array_off);
3205
3206 bfd_putl32 (EIHD__K_EXE, eihd.imgtype);
3207 bfd_putl32 (0, eihd.subtype);
3208
3209 bfd_putl32 (0, eihd.imgiocnt);
3210 bfd_putl32 (-1, eihd.privreqs);
3211 bfd_putl32 (-1, eihd.privreqs + 4);
3212
3213 bfd_putl32 ((sizeof (eihd) + VMS_BLOCK_SIZE - 1) / VMS_BLOCK_SIZE,
07d6d2b8 3214 eihd.hdrblkcnt);
95e34ef7
TG
3215 bfd_putl32 (0, eihd.ident);
3216 bfd_putl32 (0, eihd.sysver);
3217
3218 eihd.matchctl = 0;
3219 bfd_putl32 (0, eihd.symvect_size);
3220 bfd_putl32 (16, eihd.virt_mem_block_size);
3221 bfd_putl32 (0, eihd.ext_fixup_off);
3222 bfd_putl32 (0, eihd.noopt_psect_off);
3223 bfd_putl32 (-1, eihd.alias);
3224
3225 /* Alloc EIHA. */
3226 eiha = (struct vms_eiha *)((char *) &eihd + PRIV (file_pos));
3227 bfd_putl32 (PRIV (file_pos), eihd.activoff);
3228 PRIV (file_pos) += sizeof (struct vms_eiha);
3229
3230 bfd_putl32 (sizeof (struct vms_eiha), eiha->size);
3231 bfd_putl32 (0, eiha->spare);
46d00b8a
TG
3232 bfd_putl64 (PRIV (transfer_address[0]), eiha->tfradr1);
3233 bfd_putl64 (PRIV (transfer_address[1]), eiha->tfradr2);
3234 bfd_putl64 (PRIV (transfer_address[2]), eiha->tfradr3);
3235 bfd_putl64 (PRIV (transfer_address[3]), eiha->tfradr4);
95e34ef7
TG
3236 bfd_putl64 (0, eiha->inishr);
3237
3238 /* Alloc EIHI. */
3239 eihi = (struct vms_eihi *)((char *) &eihd + PRIV (file_pos));
3240 bfd_putl32 (PRIV (file_pos), eihd.imgidoff);
3241 PRIV (file_pos) += sizeof (struct vms_eihi);
3242
3243 bfd_putl32 (EIHI__K_MAJORID, eihi->majorid);
3244 bfd_putl32 (EIHI__K_MINORID, eihi->minorid);
3245 {
3246 char *module;
3247 unsigned int len;
3248
9714ee48 3249 /* Set module name. */
95e34ef7
TG
3250 module = vms_get_module_name (bfd_get_filename (abfd), TRUE);
3251 len = strlen (module);
3252 if (len > sizeof (eihi->imgnam) - 1)
3253 len = sizeof (eihi->imgnam) - 1;
3254 eihi->imgnam[0] = len;
3255 memcpy (eihi->imgnam + 1, module, len);
3256 free (module);
3257 }
9714ee48
TG
3258 {
3259 unsigned int lo;
3260 unsigned int hi;
3261
3262 /* Set time. */
3263 vms_get_time (&hi, &lo);
3264 bfd_putl32 (lo, eihi->linktime + 0);
3265 bfd_putl32 (hi, eihi->linktime + 4);
3266 }
95e34ef7
TG
3267 eihi->imgid[0] = 0;
3268 eihi->linkid[0] = 0;
3269 eihi->imgbid[0] = 0;
3270
3271 /* Alloc EIHS. */
44273c5b
TG
3272 dst = PRIV (dst_section);
3273 dmt = bfd_get_section_by_name (abfd, "$DMT$");
95e34ef7
TG
3274 if (dst != NULL && dst->size != 0)
3275 {
3276 eihs = (struct vms_eihs *)((char *) &eihd + PRIV (file_pos));
3277 bfd_putl32 (PRIV (file_pos), eihd.symdbgoff);
3278 PRIV (file_pos) += sizeof (struct vms_eihs);
3279
3280 bfd_putl32 (EIHS__K_MAJORID, eihs->majorid);
3281 bfd_putl32 (EIHS__K_MINORID, eihs->minorid);
3282 bfd_putl32 (0, eihs->dstvbn);
3283 bfd_putl32 (0, eihs->dstsize);
3284 bfd_putl32 (0, eihs->gstvbn);
3285 bfd_putl32 (0, eihs->gstsize);
3286 bfd_putl32 (0, eihs->dmtvbn);
3287 bfd_putl32 (0, eihs->dmtsize);
3288 }
3289
44273c5b 3290 /* One EISD per section. */
95e34ef7
TG
3291 for (sec = abfd->sections; sec; sec = sec->next)
3292 {
3293 if (!alpha_vms_create_eisd_for_section (abfd, sec))
07d6d2b8 3294 return FALSE;
95e34ef7
TG
3295 }
3296
3297 /* Merge section EIDS which extra ones. */
3298 if (PRIV (eisd_tail))
3299 PRIV (eisd_tail)->next = PRIV (gbl_eisd_head);
3300 else
3301 PRIV (eisd_head) = PRIV (gbl_eisd_head);
3302 if (PRIV (gbl_eisd_tail))
3303 PRIV (eisd_tail) = PRIV (gbl_eisd_tail);
3304
3305 first_eisd = PRIV (eisd_head);
3306
3307 /* Add end of eisd. */
3308 if (first_eisd)
3309 {
3310 eisd = bfd_zalloc (abfd, sizeof (*eisd));
3311 if (eisd == NULL)
07d6d2b8 3312 return FALSE;
95e34ef7
TG
3313 eisd->u.eisd.majorid = 0;
3314 eisd->u.eisd.minorid = 0;
3315 eisd->u.eisd.eisdsize = 0;
3316 alpha_vms_append_extra_eisd (abfd, eisd);
3317 }
3318
3319 /* Place EISD in the file. */
3320 for (eisd = first_eisd; eisd; eisd = eisd->next)
3321 {
3322 file_ptr room = VMS_BLOCK_SIZE - (PRIV (file_pos) % VMS_BLOCK_SIZE);
3323
3324 /* First block is a little bit special: there is a word at the end. */
3325 if (PRIV (file_pos) < VMS_BLOCK_SIZE && room > 2)
07d6d2b8 3326 room -= 2;
95e34ef7 3327 if (room < eisd->u.eisd.eisdsize + EISD__K_LENEND)
07d6d2b8 3328 alpha_vms_file_position_block (abfd);
95e34ef7
TG
3329
3330 eisd->file_pos = PRIV (file_pos);
3331 PRIV (file_pos) += eisd->u.eisd.eisdsize;
3332
3333 if (eisd->u.eisd.flags & EISD__M_FIXUPVEC)
07d6d2b8 3334 bfd_putl64 (eisd->u.eisd.virt_addr, eihd.iafva);
95e34ef7
TG
3335 }
3336
3337 if (first_eisd != NULL)
3338 {
3339 bfd_putl32 (first_eisd->file_pos, eihd.isdoff);
3340 /* Real size of end of eisd marker. */
3341 PRIV (file_pos) += EISD__K_LENEND;
3342 }
3343
3344 bfd_putl32 (PRIV (file_pos), eihd.size);
3345 bfd_putl32 ((PRIV (file_pos) + VMS_BLOCK_SIZE - 1) / VMS_BLOCK_SIZE,
07d6d2b8 3346 eihd.hdrblkcnt);
95e34ef7
TG
3347
3348 /* Place sections. */
3349 for (sec = abfd->sections; sec; sec = sec->next)
3350 {
3351 if (!(sec->flags & SEC_HAS_CONTENTS))
07d6d2b8 3352 continue;
95e34ef7
TG
3353
3354 eisd = vms_section_data (sec)->eisd;
3355
3356 /* Align on a block. */
3357 alpha_vms_file_position_block (abfd);
3358 sec->filepos = PRIV (file_pos);
3359
3360 if (eisd != NULL)
07d6d2b8 3361 eisd->u.eisd.vbn = (sec->filepos / VMS_BLOCK_SIZE) + 1;
95e34ef7
TG
3362
3363 PRIV (file_pos) += sec->size;
3364 }
3365
5fe88cfb 3366 /* Update EIHS. */
95e34ef7
TG
3367 if (eihs != NULL && dst != NULL)
3368 {
3369 bfd_putl32 ((dst->filepos / VMS_BLOCK_SIZE) + 1, eihs->dstvbn);
3370 bfd_putl32 (dst->size, eihs->dstsize);
44273c5b
TG
3371
3372 if (dmt != NULL)
07d6d2b8
AM
3373 {
3374 lnkflags |= EIHD__M_DBGDMT;
3375 bfd_putl32 ((dmt->filepos / VMS_BLOCK_SIZE) + 1, eihs->dmtvbn);
3376 bfd_putl32 (dmt->size, eihs->dmtsize);
3377 }
f9eeb9c9 3378 if (PRIV (gsd_sym_count) != 0)
07d6d2b8
AM
3379 {
3380 alpha_vms_file_position_block (abfd);
3381 gst_filepos = PRIV (file_pos);
3382 bfd_putl32 ((gst_filepos / VMS_BLOCK_SIZE) + 1, eihs->gstvbn);
3383 bfd_putl32 ((PRIV (gsd_sym_count) + 4) / 5 + 4, eihs->gstsize);
3384 }
95e34ef7
TG
3385 }
3386
3387 /* Write EISD in hdr. */
3388 for (eisd = first_eisd; eisd && eisd->file_pos < VMS_BLOCK_SIZE;
3389 eisd = eisd->next)
3390 alpha_vms_swap_eisd_out
3391 (eisd, (struct vms_eisd *)((char *)&eihd + eisd->file_pos));
3392
3393 /* Write first block. */
f9eeb9c9 3394 bfd_putl32 (lnkflags, eihd.lnkflags);
95e34ef7
TG
3395 if (bfd_bwrite (&eihd, sizeof (eihd), abfd) != sizeof (eihd))
3396 return FALSE;
3397
3398 /* Write remaining eisd. */
3399 if (eisd != NULL)
3400 {
3401 unsigned char blk[VMS_BLOCK_SIZE];
3402 struct vms_internal_eisd_map *next_eisd;
3403
3404 memset (blk, 0xff, sizeof (blk));
3405 while (eisd != NULL)
07d6d2b8
AM
3406 {
3407 alpha_vms_swap_eisd_out
3408 (eisd,
3409 (struct vms_eisd *)(blk + (eisd->file_pos % VMS_BLOCK_SIZE)));
3410
3411 next_eisd = eisd->next;
3412 if (next_eisd == NULL
3413 || (next_eisd->file_pos / VMS_BLOCK_SIZE
3414 != eisd->file_pos / VMS_BLOCK_SIZE))
3415 {
3416 if (bfd_bwrite (blk, sizeof (blk), abfd) != sizeof (blk))
3417 return FALSE;
95e34ef7 3418
07d6d2b8
AM
3419 memset (blk, 0xff, sizeof (blk));
3420 }
3421 eisd = next_eisd;
3422 }
95e34ef7
TG
3423 }
3424
3425 /* Write sections. */
3426 for (sec = abfd->sections; sec; sec = sec->next)
3427 {
3428 unsigned char blk[VMS_BLOCK_SIZE];
3429 bfd_size_type len;
3430
3431 if (sec->size == 0 || !(sec->flags & SEC_HAS_CONTENTS))
07d6d2b8 3432 continue;
95e34ef7 3433 if (bfd_bwrite (sec->contents, sec->size, abfd) != sec->size)
07d6d2b8 3434 return FALSE;
95e34ef7
TG
3435
3436 /* Pad. */
3437 len = VMS_BLOCK_SIZE - sec->size % VMS_BLOCK_SIZE;
3438 if (len != VMS_BLOCK_SIZE)
07d6d2b8
AM
3439 {
3440 memset (blk, 0, len);
3441 if (bfd_bwrite (blk, len, abfd) != len)
3442 return FALSE;
3443 }
95e34ef7
TG
3444 }
3445
f9eeb9c9
TG
3446 /* Write GST. */
3447 if (gst_filepos != 0)
3448 {
3449 struct vms_rec_wr *recwr = &PRIV (recwr);
3450 unsigned int i;
3451
3452 _bfd_vms_write_emh (abfd);
3453 _bfd_vms_write_lmn (abfd, "GNU LD");
3454
3455 /* PSC for the absolute section. */
3456 _bfd_vms_output_begin (recwr, EOBJ__C_EGSD);
3457 _bfd_vms_output_long (recwr, 0);
3458 _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC);
3459 _bfd_vms_output_short (recwr, 0);
3460 _bfd_vms_output_short (recwr, EGPS__V_PIC | EGPS__V_LIB | EGPS__V_RD);
3461 _bfd_vms_output_long (recwr, 0);
3462 _bfd_vms_output_counted (recwr, ".$$ABS$$.");
3463 _bfd_vms_output_end_subrec (recwr);
3464 _bfd_vms_output_end (abfd, recwr);
3465
3466 for (i = 0; i < PRIV (gsd_sym_count); i++)
07d6d2b8
AM
3467 {
3468 struct vms_symbol_entry *sym = PRIV (syms)[i];
3469 bfd_vma val;
3470 bfd_vma ep;
3471
3472 if ((i % 5) == 0)
3473 {
3474 _bfd_vms_output_alignment (recwr, 8);
3475 _bfd_vms_output_begin (recwr, EOBJ__C_EGSD);
3476 _bfd_vms_output_long (recwr, 0);
3477 }
3478 _bfd_vms_output_begin_subrec (recwr, EGSD__C_SYMG);
3479 _bfd_vms_output_short (recwr, 0); /* Data type, alignment. */
3480 _bfd_vms_output_short (recwr, sym->flags);
3481
3482 if (sym->code_section)
3483 ep = alpha_vms_get_sym_value (sym->code_section, sym->code_value);
3484 else
3485 {
3486 BFD_ASSERT (sym->code_value == 0);
3487 ep = 0;
3488 }
3489 val = alpha_vms_get_sym_value (sym->section, sym->value);
3490 _bfd_vms_output_quad
3491 (recwr, sym->typ == EGSD__C_SYMG ? sym->symbol_vector : val);
3492 _bfd_vms_output_quad (recwr, ep);
3493 _bfd_vms_output_quad (recwr, val);
3494 _bfd_vms_output_long (recwr, 0);
3495 _bfd_vms_output_counted (recwr, sym->name);
3496 _bfd_vms_output_end_subrec (recwr);
3497 if ((i % 5) == 4)
3498 _bfd_vms_output_end (abfd, recwr);
3499 }
f9eeb9c9 3500 if ((i % 5) != 0)
07d6d2b8 3501 _bfd_vms_output_end (abfd, recwr);
f9eeb9c9
TG
3502
3503 if (!_bfd_vms_write_eeom (abfd))
07d6d2b8 3504 return FALSE;
f9eeb9c9 3505 }
95e34ef7
TG
3506 return TRUE;
3507}
3508\f
3509/* Object write. */
3510
95e34ef7
TG
3511/* Write section and symbol directory of bfd abfd. Return FALSE on error. */
3512
3513static bfd_boolean
3514_bfd_vms_write_egsd (bfd *abfd)
3515{
3516 asection *section;
3517 asymbol *symbol;
3518 unsigned int symnum;
dddb0e80 3519 const char *sname;
95e34ef7 3520 flagword new_flags, old_flags;
4ba2ab9f 3521 int abs_section_index = -1;
1b3d1dbf 3522 unsigned int target_index = 0;
95e34ef7
TG
3523 struct vms_rec_wr *recwr = &PRIV (recwr);
3524
1b3d1dbf 3525 vms_debug2 ((2, "vms_write_egsd\n"));
95e34ef7
TG
3526
3527 /* Egsd is quadword aligned. */
3528 _bfd_vms_output_alignment (recwr, 8);
3529
3530 _bfd_vms_output_begin (recwr, EOBJ__C_EGSD);
3531 _bfd_vms_output_long (recwr, 0);
3532
1b3d1dbf
TG
3533 /* Number sections. */
3534 for (section = abfd->sections; section != NULL; section = section->next)
3535 {
3536 if (section->flags & SEC_DEBUGGING)
07d6d2b8 3537 continue;
1b3d1dbf 3538 if (!strcmp (section->name, ".vmsdebug"))
07d6d2b8
AM
3539 {
3540 section->flags |= SEC_DEBUGGING;
3541 continue;
3542 }
1b3d1dbf
TG
3543 section->target_index = target_index++;
3544 }
3545
3546 for (section = abfd->sections; section != NULL; section = section->next)
95e34ef7
TG
3547 {
3548 vms_debug2 ((3, "Section #%d %s, %d bytes\n",
07d6d2b8 3549 section->target_index, section->name, (int)section->size));
95e34ef7
TG
3550
3551 /* Don't write out the VMS debug info section since it is in the
07d6d2b8 3552 ETBT and EDBG sections in etir. */
1b3d1dbf 3553 if (section->flags & SEC_DEBUGGING)
07d6d2b8 3554 continue;
95e34ef7
TG
3555
3556 /* 13 bytes egsd, max 31 chars name -> should be 44 bytes. */
3557 if (_bfd_vms_output_check (recwr, 64) < 0)
3558 {
3559 _bfd_vms_output_end (abfd, recwr);
3560 _bfd_vms_output_begin (recwr, EOBJ__C_EGSD);
3561 _bfd_vms_output_long (recwr, 0);
3562 }
3563
95e34ef7 3564 /* Don't know if this is necessary for the linker but for now it keeps
5fe88cfb 3565 vms_slurp_gsd happy. */
81bb31c0 3566 sname = section->name;
95e34ef7
TG
3567 if (*sname == '.')
3568 {
07d6d2b8 3569 /* Remove leading dot. */
95e34ef7
TG
3570 sname++;
3571 if ((*sname == 't') && (strcmp (sname, "text") == 0))
3572 sname = EVAX_CODE_NAME;
3573 else if ((*sname == 'd') && (strcmp (sname, "data") == 0))
3574 sname = EVAX_DATA_NAME;
3575 else if ((*sname == 'b') && (strcmp (sname, "bss") == 0))
3576 sname = EVAX_BSS_NAME;
3577 else if ((*sname == 'l') && (strcmp (sname, "link") == 0))
3578 sname = EVAX_LINK_NAME;
3579 else if ((*sname == 'r') && (strcmp (sname, "rdata") == 0))
3580 sname = EVAX_READONLY_NAME;
3581 else if ((*sname == 'l') && (strcmp (sname, "literal") == 0))
3582 sname = EVAX_LITERAL_NAME;
3583 else if ((*sname == 'l') && (strcmp (sname, "literals") == 0))
07d6d2b8 3584 sname = EVAX_LITERALS_NAME;
95e34ef7
TG
3585 else if ((*sname == 'c') && (strcmp (sname, "comm") == 0))
3586 sname = EVAX_COMMON_NAME;
3587 else if ((*sname == 'l') && (strcmp (sname, "lcomm") == 0))
3588 sname = EVAX_LOCAL_NAME;
3589 }
95e34ef7 3590
95e34ef7
TG
3591 if (bfd_is_com_section (section))
3592 new_flags = (EGPS__V_OVR | EGPS__V_REL | EGPS__V_GBL | EGPS__V_RD
3593 | EGPS__V_WRT | EGPS__V_NOMOD | EGPS__V_COM);
3594 else
3595 new_flags = vms_esecflag_by_name (evax_section_flags, sname,
3596 section->size > 0);
3597
3598 /* Modify them as directed. */
3599 if (section->flags & SEC_READONLY)
3600 new_flags &= ~EGPS__V_WRT;
3601
3602 new_flags &= ~vms_section_data (section)->no_flags;
3603 new_flags |= vms_section_data (section)->flags;
3604
3605 vms_debug2 ((3, "sec flags %x\n", section->flags));
3606 vms_debug2 ((3, "new_flags %x, _raw_size %lu\n",
07d6d2b8 3607 new_flags, (unsigned long)section->size));
95e34ef7 3608
4ba2ab9f
TG
3609 _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC);
3610 _bfd_vms_output_short (recwr, section->alignment_power & 0xff);
95e34ef7
TG
3611 _bfd_vms_output_short (recwr, new_flags);
3612 _bfd_vms_output_long (recwr, (unsigned long) section->size);
3613 _bfd_vms_output_counted (recwr, sname);
3614 _bfd_vms_output_end_subrec (recwr);
4ba2ab9f
TG
3615
3616 /* If the section is an obsolute one, remind its index as it will be
07d6d2b8 3617 used later for absolute symbols. */
4ba2ab9f 3618 if ((new_flags & EGPS__V_REL) == 0 && abs_section_index < 0)
07d6d2b8 3619 abs_section_index = section->target_index;
95e34ef7
TG
3620 }
3621
3622 /* Output symbols. */
3623 vms_debug2 ((3, "%d symbols found\n", abfd->symcount));
3624
3625 bfd_set_start_address (abfd, (bfd_vma) -1);
3626
3627 for (symnum = 0; symnum < abfd->symcount; symnum++)
3628 {
95e34ef7 3629 symbol = abfd->outsymbols[symnum];
46d00b8a
TG
3630 old_flags = symbol->flags;
3631
4ba2ab9f 3632 /* Work-around a missing feature: consider __main as the main entry
07d6d2b8 3633 point. */
53452371
TG
3634 if (symbol->name[0] == '_' && strcmp (symbol->name, "__main") == 0)
3635 bfd_set_start_address (abfd, (bfd_vma)symbol->value);
95e34ef7 3636
46d00b8a 3637 /* Only put in the GSD the global and the undefined symbols. */
95e34ef7
TG
3638 if (old_flags & BSF_FILE)
3639 continue;
3640
46d00b8a 3641 if ((old_flags & BSF_GLOBAL) == 0 && !bfd_is_und_section (symbol->section))
07d6d2b8
AM
3642 {
3643 /* If the LIB$INITIIALIZE section is present, add a reference to
3644 LIB$INITIALIZE symbol. FIXME: this should be done explicitely
3645 in the assembly file. */
3646 if (!((old_flags & BSF_SECTION_SYM) != 0
3647 && strcmp (symbol->section->name, "LIB$INITIALIZE") == 0))
3648 continue;
3649 }
95e34ef7 3650
4ba2ab9f 3651 /* 13 bytes egsd, max 64 chars name -> should be 77 bytes. Add 16 more
07d6d2b8 3652 bytes for a possible ABS section. */
4ba2ab9f 3653 if (_bfd_vms_output_check (recwr, 80 + 16) < 0)
95e34ef7
TG
3654 {
3655 _bfd_vms_output_end (abfd, recwr);
3656 _bfd_vms_output_begin (recwr, EOBJ__C_EGSD);
3657 _bfd_vms_output_long (recwr, 0);
3658 }
3659
4ba2ab9f 3660 if ((old_flags & BSF_GLOBAL) != 0
07d6d2b8
AM
3661 && bfd_is_abs_section (symbol->section)
3662 && abs_section_index <= 0)
3663 {
3664 /* Create an absolute section if none was defined. It is highly
3665 unlikely that the name $ABS$ clashes with a user defined
3666 non-absolute section name. */
3667 _bfd_vms_output_begin_subrec (recwr, EGSD__C_PSC);
3668 _bfd_vms_output_short (recwr, 4);
3669 _bfd_vms_output_short (recwr, EGPS__V_SHR);
3670 _bfd_vms_output_long (recwr, 0);
3671 _bfd_vms_output_counted (recwr, "$ABS$");
3672 _bfd_vms_output_end_subrec (recwr);
3673
3674 abs_section_index = target_index++;
3675 }
4ba2ab9f 3676
95e34ef7
TG
3677 _bfd_vms_output_begin_subrec (recwr, EGSD__C_SYM);
3678
3679 /* Data type, alignment. */
3680 _bfd_vms_output_short (recwr, 0);
3681
3682 new_flags = 0;
3683
3684 if (old_flags & BSF_WEAK)
3685 new_flags |= EGSY__V_WEAK;
3686 if (bfd_is_com_section (symbol->section)) /* .comm */
3687 new_flags |= (EGSY__V_WEAK | EGSY__V_COMM);
3688
3689 if (old_flags & BSF_FUNCTION)
3690 {
3691 new_flags |= EGSY__V_NORM;
3692 new_flags |= EGSY__V_REL;
3693 }
3694 if (old_flags & BSF_GLOBAL)
3695 {
3696 new_flags |= EGSY__V_DEF;
3697 if (!bfd_is_abs_section (symbol->section))
3698 new_flags |= EGSY__V_REL;
3699 }
3700 _bfd_vms_output_short (recwr, new_flags);
3701
3702 if (old_flags & BSF_GLOBAL)
3703 {
3704 /* Symbol definition. */
3705 bfd_vma code_address = 0;
3706 unsigned long ca_psindx = 0;
3707 unsigned long psindx;
3708
3709 if ((old_flags & BSF_FUNCTION) && symbol->udata.p != NULL)
3710 {
3711 asymbol *sym;
3712
07d6d2b8
AM
3713 sym =
3714 ((struct evax_private_udata_struct *)symbol->udata.p)->enbsym;
95e34ef7 3715 code_address = sym->value;
1b3d1dbf 3716 ca_psindx = sym->section->target_index;
95e34ef7
TG
3717 }
3718 if (bfd_is_abs_section (symbol->section))
3719 psindx = abs_section_index;
3720 else
1b3d1dbf 3721 psindx = symbol->section->target_index;
95e34ef7
TG
3722
3723 _bfd_vms_output_quad (recwr, symbol->value);
3724 _bfd_vms_output_quad (recwr, code_address);
3725 _bfd_vms_output_long (recwr, ca_psindx);
3726 _bfd_vms_output_long (recwr, psindx);
3727 }
53452371 3728 _bfd_vms_output_counted (recwr, symbol->name);
95e34ef7
TG
3729
3730 _bfd_vms_output_end_subrec (recwr);
95e34ef7
TG
3731 }
3732
3733 _bfd_vms_output_alignment (recwr, 8);
3734 _bfd_vms_output_end (abfd, recwr);
3735
3736 return TRUE;
3737}
3738
3739/* Write object header for bfd abfd. Return FALSE on error. */
3740
3741static bfd_boolean
3742_bfd_vms_write_ehdr (bfd *abfd)
3743{
3744 asymbol *symbol;
3745 unsigned int symnum;
95e34ef7
TG
3746 struct vms_rec_wr *recwr = &PRIV (recwr);
3747
3748 vms_debug2 ((2, "vms_write_ehdr (%p)\n", abfd));
3749
3750 _bfd_vms_output_alignment (recwr, 2);
3751
bd7b51b4
TG
3752 _bfd_vms_write_emh (abfd);
3753 _bfd_vms_write_lmn (abfd, "GNU AS");
95e34ef7
TG
3754
3755 /* SRC. */
3756 _bfd_vms_output_begin (recwr, EOBJ__C_EMH);
3757 _bfd_vms_output_short (recwr, EMH__C_SRC);
3758
3759 for (symnum = 0; symnum < abfd->symcount; symnum++)
3760 {
3761 symbol = abfd->outsymbols[symnum];
3762
3763 if (symbol->flags & BSF_FILE)
3764 {
95e34ef7
TG
3765 _bfd_vms_output_dump (recwr, (unsigned char *) symbol->name,
3766 (int) strlen (symbol->name));
53452371 3767 break;
95e34ef7
TG
3768 }
3769 }
3770
3771 if (symnum == abfd->symcount)
3772 _bfd_vms_output_dump (recwr, (unsigned char *) STRING_COMMA_LEN ("noname"));
3773
3774 _bfd_vms_output_end (abfd, recwr);
3775
3776 /* TTL. */
3777 _bfd_vms_output_begin (recwr, EOBJ__C_EMH);
3778 _bfd_vms_output_short (recwr, EMH__C_TTL);
3779 _bfd_vms_output_dump (recwr, (unsigned char *) STRING_COMMA_LEN ("TTL"));
3780 _bfd_vms_output_end (abfd, recwr);
3781
3782 /* CPR. */
3783 _bfd_vms_output_begin (recwr, EOBJ__C_EMH);
3784 _bfd_vms_output_short (recwr, EMH__C_CPR);
3785 _bfd_vms_output_dump (recwr,
07d6d2b8 3786 (unsigned char *)"GNU BFD ported by Klaus Kämpf 1994-1996",
95e34ef7
TG
3787 39);
3788 _bfd_vms_output_end (abfd, recwr);
3789
3790 return TRUE;
3791}
3792
3793/* Part 4.6, relocations. */
3794
3795\f
3796/* WRITE ETIR SECTION
3797
3798 This is still under construction and therefore not documented. */
3799
3800/* Close the etir/etbt record. */
3801
3802static void
3803end_etir_record (bfd * abfd)
3804{
3805 struct vms_rec_wr *recwr = &PRIV (recwr);
3806
3807 _bfd_vms_output_end (abfd, recwr);
3808}
3809
3810static void
3811start_etir_or_etbt_record (bfd *abfd, asection *section, bfd_vma offset)
3812{
3813 struct vms_rec_wr *recwr = &PRIV (recwr);
3814
1b3d1dbf 3815 if (section->flags & SEC_DEBUGGING)
95e34ef7
TG
3816 {
3817 _bfd_vms_output_begin (recwr, EOBJ__C_ETBT);
3818
3819 if (offset == 0)
07d6d2b8
AM
3820 {
3821 /* Push start offset. */
3822 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW);
3823 _bfd_vms_output_long (recwr, (unsigned long) 0);
3824 _bfd_vms_output_end_subrec (recwr);
3825
3826 /* Set location. */
3827 _bfd_vms_output_begin_subrec (recwr, ETIR__C_CTL_DFLOC);
3828 _bfd_vms_output_end_subrec (recwr);
3829 }
95e34ef7
TG
3830 }
3831 else
3832 {
3833 _bfd_vms_output_begin (recwr, EOBJ__C_ETIR);
3834
3835 if (offset == 0)
07d6d2b8
AM
3836 {
3837 /* Push start offset. */
3838 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ);
3839 _bfd_vms_output_long (recwr, (unsigned long) section->target_index);
3840 _bfd_vms_output_quad (recwr, offset);
3841 _bfd_vms_output_end_subrec (recwr);
3842
3843 /* Start = pop (). */
3844 _bfd_vms_output_begin_subrec (recwr, ETIR__C_CTL_SETRB);
3845 _bfd_vms_output_end_subrec (recwr);
3846 }
95e34ef7
TG
3847 }
3848}
3849
3850/* Output a STO_IMM command for SSIZE bytes of data from CPR at virtual
3851 address VADDR in section specified by SEC_INDEX and NAME. */
3852
3853static void
3854sto_imm (bfd *abfd, asection *section,
07d6d2b8 3855 bfd_size_type ssize, unsigned char *cptr, bfd_vma vaddr)
95e34ef7
TG
3856{
3857 bfd_size_type size;
3858 struct vms_rec_wr *recwr = &PRIV (recwr);
3859
3860#if VMS_DEBUG
3861 _bfd_vms_debug (8, "sto_imm %d bytes\n", (int) ssize);
3862 _bfd_hexdump (9, cptr, (int) ssize, (int) vaddr);
3863#endif
3864
3865 while (ssize > 0)
3866 {
3867 /* Try all the rest. */
3868 size = ssize;
3869
3870 if (_bfd_vms_output_check (recwr, size) < 0)
3871 {
3872 /* Doesn't fit, split ! */
3873 end_etir_record (abfd);
3874
07d6d2b8 3875 start_etir_or_etbt_record (abfd, section, vaddr);
95e34ef7
TG
3876
3877 size = _bfd_vms_output_check (recwr, 0); /* get max size */
3878 if (size > ssize) /* more than what's left ? */
3879 size = ssize;
3880 }
3881
3882 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_IMM);
3883 _bfd_vms_output_long (recwr, (unsigned long) (size));
3884 _bfd_vms_output_dump (recwr, cptr, size);
3885 _bfd_vms_output_end_subrec (recwr);
3886
3887#if VMS_DEBUG
3888 _bfd_vms_debug (10, "dumped %d bytes\n", (int) size);
3889 _bfd_hexdump (10, cptr, (int) size, (int) vaddr);
3890#endif
3891
3892 vaddr += size;
3893 cptr += size;
3894 ssize -= size;
3895 }
3896}
3897
3898static void
3899etir_output_check (bfd *abfd, asection *section, bfd_vma vaddr, int checklen)
3900{
3901 if (_bfd_vms_output_check (&PRIV (recwr), checklen) < 0)
3902 {
3903 /* Not enough room in this record. Close it and open a new one. */
3904 end_etir_record (abfd);
3905 start_etir_or_etbt_record (abfd, section, vaddr);
3906 }
3907}
3908
3909/* Return whether RELOC must be deferred till the end. */
3910
3911static bfd_boolean
3912defer_reloc_p (arelent *reloc)
3913{
3914 switch (reloc->howto->type)
3915 {
3916 case ALPHA_R_NOP:
3917 case ALPHA_R_LDA:
3918 case ALPHA_R_BSR:
3919 case ALPHA_R_BOH:
3920 return TRUE;
3921
3922 default:
3923 return FALSE;
3924 }
3925}
3926
3927/* Write section contents for bfd abfd. Return FALSE on error. */
3928
3929static bfd_boolean
3930_bfd_vms_write_etir (bfd * abfd, int objtype ATTRIBUTE_UNUSED)
3931{
3932 asection *section;
3933 struct vms_rec_wr *recwr = &PRIV (recwr);
3934
3935 vms_debug2 ((2, "vms_write_tir (%p, %d)\n", abfd, objtype));
3936
3937 _bfd_vms_output_alignment (recwr, 4);
3938
f1bb0388 3939 PRIV (vms_linkage_index) = 0;
95e34ef7
TG
3940
3941 for (section = abfd->sections; section; section = section->next)
3942 {
3943 vms_debug2 ((4, "writing %d. section '%s' (%d bytes)\n",
07d6d2b8 3944 section->target_index, section->name, (int) (section->size)));
95e34ef7
TG
3945
3946 if (!(section->flags & SEC_HAS_CONTENTS)
3947 || bfd_is_com_section (section))
3948 continue;
3949
3950 if (!section->contents)
3951 {
3952 bfd_set_error (bfd_error_no_contents);
3953 return FALSE;
3954 }
3955
3956 start_etir_or_etbt_record (abfd, section, 0);
3957
3958 if (section->flags & SEC_RELOC)
3959 {
3960 bfd_vma curr_addr = 0;
3961 unsigned char *curr_data = section->contents;
3962 bfd_size_type size;
3963 int pass2_needed = 0;
3964 int pass2_in_progress = 0;
3965 unsigned int irel;
3966
083faca9 3967 if (section->reloc_count == 0)
4eca0228 3968 _bfd_error_handler
871b3ab2 3969 (_("SEC_RELOC with no relocs in section %pA"), section);
95e34ef7
TG
3970
3971#if VMS_DEBUG
3972 else
3973 {
3974 int i = section->reloc_count;
3975 arelent **rptr = section->orelocation;
3976 _bfd_vms_debug (4, "%d relocations:\n", i);
3977 while (i-- > 0)
3978 {
3979 _bfd_vms_debug (4, "sym %s in sec %s, value %08lx, "
3980 "addr %08lx, off %08lx, len %d: %s\n",
3981 (*(*rptr)->sym_ptr_ptr)->name,
3982 (*(*rptr)->sym_ptr_ptr)->section->name,
3983 (long) (*(*rptr)->sym_ptr_ptr)->value,
3984 (unsigned long)(*rptr)->address,
07d6d2b8 3985 (unsigned long)(*rptr)->addend,
95e34ef7 3986 bfd_get_reloc_size ((*rptr)->howto),
07d6d2b8 3987 ( *rptr)->howto->name);
95e34ef7
TG
3988 rptr++;
3989 }
3990 }
3991#endif
3992
3993 new_pass:
3994 for (irel = 0; irel < section->reloc_count; irel++)
3995 {
3996 struct evax_private_udata_struct *udata;
3997 arelent *rptr = section->orelocation [irel];
3998 bfd_vma addr = rptr->address;
3999 asymbol *sym = *rptr->sym_ptr_ptr;
4000 asection *sec = sym->section;
4001 bfd_boolean defer = defer_reloc_p (rptr);
4002 unsigned int slen;
95e34ef7
TG
4003
4004 if (pass2_in_progress)
4005 {
4006 /* Non-deferred relocs have already been output. */
4007 if (!defer)
4008 continue;
4009 }
4010 else
4011 {
4012 /* Deferred relocs must be output at the very end. */
4013 if (defer)
4014 {
4015 pass2_needed = 1;
4016 continue;
4017 }
4018
4019 /* Regular relocs are intertwined with binary data. */
07d6d2b8 4020 if (curr_addr > addr)
38f14ab8 4021 _bfd_error_handler (_("size error in section %pA"),
dae82561 4022 section);
95e34ef7
TG
4023 size = addr - curr_addr;
4024 sto_imm (abfd, section, size, curr_data, curr_addr);
4025 curr_data += size;
4026 curr_addr += size;
4027 }
4028
4029 size = bfd_get_reloc_size (rptr->howto);
4030
4031 switch (rptr->howto->type)
07d6d2b8 4032 {
95e34ef7
TG
4033 case ALPHA_R_IGNORE:
4034 break;
4035
4036 case ALPHA_R_REFLONG:
4037 if (bfd_is_und_section (sym->section))
4038 {
4039 bfd_vma addend = rptr->addend;
4040 slen = strlen ((char *) sym->name);
95e34ef7
TG
4041 etir_output_check (abfd, section, curr_addr, slen);
4042 if (addend)
4043 {
4044 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_GBL);
53452371 4045 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4046 _bfd_vms_output_end_subrec (recwr);
4047 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW);
4048 _bfd_vms_output_long (recwr, (unsigned long) addend);
4049 _bfd_vms_output_end_subrec (recwr);
4050 _bfd_vms_output_begin_subrec (recwr, ETIR__C_OPR_ADD);
4051 _bfd_vms_output_end_subrec (recwr);
4052 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW);
4053 _bfd_vms_output_end_subrec (recwr);
4054 }
4055 else
4056 {
4057 _bfd_vms_output_begin_subrec
07d6d2b8 4058 (recwr, ETIR__C_STO_GBL_LW);
53452371 4059 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4060 _bfd_vms_output_end_subrec (recwr);
4061 }
4062 }
4063 else if (bfd_is_abs_section (sym->section))
4064 {
4065 etir_output_check (abfd, section, curr_addr, 16);
4066 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_LW);
4067 _bfd_vms_output_long (recwr, (unsigned long) sym->value);
4068 _bfd_vms_output_end_subrec (recwr);
4069 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW);
4070 _bfd_vms_output_end_subrec (recwr);
4071 }
4072 else
4073 {
4074 etir_output_check (abfd, section, curr_addr, 32);
4075 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ);
1b3d1dbf 4076 _bfd_vms_output_long (recwr,
07d6d2b8 4077 (unsigned long) sec->target_index);
95e34ef7
TG
4078 _bfd_vms_output_quad (recwr, rptr->addend + sym->value);
4079 _bfd_vms_output_end_subrec (recwr);
4080 /* ??? Table B-8 of the OpenVMS Linker Utilily Manual
4081 says that we should have a ETIR__C_STO_OFF here.
4082 But the relocation would not be BFD_RELOC_32 then.
4083 This case is very likely unreachable. */
4084 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_LW);
4085 _bfd_vms_output_end_subrec (recwr);
4086 }
4087 break;
4088
4089 case ALPHA_R_REFQUAD:
4090 if (bfd_is_und_section (sym->section))
4091 {
4092 bfd_vma addend = rptr->addend;
4093 slen = strlen ((char *) sym->name);
95e34ef7
TG
4094 etir_output_check (abfd, section, curr_addr, slen);
4095 if (addend)
4096 {
4097 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_GBL);
53452371 4098 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4099 _bfd_vms_output_end_subrec (recwr);
4100 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_QW);
4101 _bfd_vms_output_quad (recwr, addend);
4102 _bfd_vms_output_end_subrec (recwr);
4103 _bfd_vms_output_begin_subrec (recwr, ETIR__C_OPR_ADD);
4104 _bfd_vms_output_end_subrec (recwr);
4105 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_QW);
4106 _bfd_vms_output_end_subrec (recwr);
4107 }
4108 else
4109 {
4110 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_GBL);
53452371 4111 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4112 _bfd_vms_output_end_subrec (recwr);
4113 }
4114 }
4115 else if (bfd_is_abs_section (sym->section))
4116 {
4117 etir_output_check (abfd, section, curr_addr, 16);
4118 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_QW);
4119 _bfd_vms_output_quad (recwr, sym->value);
4120 _bfd_vms_output_end_subrec (recwr);
4121 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_QW);
4122 _bfd_vms_output_end_subrec (recwr);
4123 }
4124 else
4125 {
4126 etir_output_check (abfd, section, curr_addr, 32);
4127 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STA_PQ);
1b3d1dbf 4128 _bfd_vms_output_long (recwr,
07d6d2b8 4129 (unsigned long) sec->target_index);
95e34ef7
TG
4130 _bfd_vms_output_quad (recwr, rptr->addend + sym->value);
4131 _bfd_vms_output_end_subrec (recwr);
4132 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_OFF);
4133 _bfd_vms_output_end_subrec (recwr);
4134 }
4135 break;
4136
4137 case ALPHA_R_HINT:
4138 sto_imm (abfd, section, size, curr_data, curr_addr);
4139 break;
4140
4141 case ALPHA_R_LINKAGE:
706704c8 4142 size = 16;
95e34ef7
TG
4143 etir_output_check (abfd, section, curr_addr, 64);
4144 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_LP_PSB);
4145 _bfd_vms_output_long
25d41743 4146 (recwr, (unsigned long) rptr->addend);
07d6d2b8
AM
4147 if (rptr->addend > PRIV (vms_linkage_index))
4148 PRIV (vms_linkage_index) = rptr->addend;
53452371 4149 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4150 _bfd_vms_output_byte (recwr, 0);
4151 _bfd_vms_output_end_subrec (recwr);
4152 break;
4153
4154 case ALPHA_R_CODEADDR:
4155 slen = strlen ((char *) sym->name);
95e34ef7
TG
4156 etir_output_check (abfd, section, curr_addr, slen);
4157 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STO_CA);
53452371 4158 _bfd_vms_output_counted (recwr, sym->name);
95e34ef7
TG
4159 _bfd_vms_output_end_subrec (recwr);
4160 break;
4161
4162 case ALPHA_R_NOP:
4163 udata
4164 = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr;
4165 etir_output_check (abfd, section, curr_addr,
4166 32 + 1 + strlen (udata->origname));
4167 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_NOP_GBL);
4168 _bfd_vms_output_long (recwr, (unsigned long) udata->lkindex);
4169 _bfd_vms_output_long
a8efca92 4170 (recwr, (unsigned long) section->target_index);
95e34ef7
TG
4171 _bfd_vms_output_quad (recwr, rptr->address);
4172 _bfd_vms_output_long (recwr, (unsigned long) 0x47ff041f);
4173 _bfd_vms_output_long
a8efca92 4174 (recwr, (unsigned long) section->target_index);
95e34ef7 4175 _bfd_vms_output_quad (recwr, rptr->addend);
53452371 4176 _bfd_vms_output_counted (recwr, udata->origname);
95e34ef7
TG
4177 _bfd_vms_output_end_subrec (recwr);
4178 break;
4179
4180 case ALPHA_R_BSR:
38f14ab8 4181 _bfd_error_handler (_("spurious ALPHA_R_BSR reloc"));
95e34ef7
TG
4182 break;
4183
4184 case ALPHA_R_LDA:
4185 udata
4186 = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr;
4187 etir_output_check (abfd, section, curr_addr,
4188 32 + 1 + strlen (udata->origname));
4189 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_LDA_GBL);
4190 _bfd_vms_output_long
4191 (recwr, (unsigned long) udata->lkindex + 1);
4192 _bfd_vms_output_long
a8efca92 4193 (recwr, (unsigned long) section->target_index);
95e34ef7
TG
4194 _bfd_vms_output_quad (recwr, rptr->address);
4195 _bfd_vms_output_long (recwr, (unsigned long) 0x237B0000);
4196 _bfd_vms_output_long
1b3d1dbf 4197 (recwr, (unsigned long) udata->bsym->section->target_index);
95e34ef7 4198 _bfd_vms_output_quad (recwr, rptr->addend);
53452371 4199 _bfd_vms_output_counted (recwr, udata->origname);
95e34ef7
TG
4200 _bfd_vms_output_end_subrec (recwr);
4201 break;
4202
4203 case ALPHA_R_BOH:
4204 udata
4205 = (struct evax_private_udata_struct *) rptr->sym_ptr_ptr;
4206 etir_output_check (abfd, section, curr_addr,
4207 32 + 1 + strlen (udata->origname));
4208 _bfd_vms_output_begin_subrec (recwr, ETIR__C_STC_BOH_GBL);
4209 _bfd_vms_output_long (recwr, (unsigned long) udata->lkindex);
4210 _bfd_vms_output_long
a8efca92 4211 (recwr, (unsigned long) section->target_index);
95e34ef7
TG
4212 _bfd_vms_output_quad (recwr, rptr->address);
4213 _bfd_vms_output_long (recwr, (unsigned long) 0xD3400000);
4214 _bfd_vms_output_long
a8efca92 4215 (recwr, (unsigned long) section->target_index);
95e34ef7 4216 _bfd_vms_output_quad (recwr, rptr->addend);
53452371 4217 _bfd_vms_output_counted (recwr, udata->origname);
95e34ef7
TG
4218 _bfd_vms_output_end_subrec (recwr);
4219 break;
4220
4221 default:
38f14ab8 4222 _bfd_error_handler (_("unhandled relocation %s"),
4eca0228 4223 rptr->howto->name);
95e34ef7
TG
4224 break;
4225 }
4226
4227 curr_data += size;
4228 curr_addr += size;
4229 } /* End of relocs loop. */
4230
4231 if (!pass2_in_progress)
4232 {
4233 /* Output rest of section. */
4234 if (curr_addr > section->size)
9ec2f606
AM
4235 {
4236 _bfd_error_handler (_("size error in section %pA"), section);
4237 return FALSE;
4238 }
95e34ef7
TG
4239 size = section->size - curr_addr;
4240 sto_imm (abfd, section, size, curr_data, curr_addr);
4241 curr_data += size;
4242 curr_addr += size;
4243
4244 if (pass2_needed)
4245 {
4246 pass2_in_progress = 1;
4247 goto new_pass;
4248 }
4249 }
4250 }
4251
4252 else /* (section->flags & SEC_RELOC) */
4253 sto_imm (abfd, section, section->size, section->contents, 0);
4254
4255 end_etir_record (abfd);
4256 }
4257
4258 _bfd_vms_output_alignment (recwr, 2);
4259 return TRUE;
4260}
4261
95e34ef7
TG
4262/* Write cached information into a file being written, at bfd_close. */
4263
4264static bfd_boolean
4265alpha_vms_write_object_contents (bfd *abfd)
4266{
4267 vms_debug2 ((1, "vms_write_object_contents (%p)\n", abfd));
4268
4269 if (abfd->flags & (EXEC_P | DYNAMIC))
4270 {
4271 return alpha_vms_write_exec (abfd);
4272 }
4273 else
4274 {
4275 if (abfd->section_count > 0) /* we have sections */
07d6d2b8
AM
4276 {
4277 if (!_bfd_vms_write_ehdr (abfd))
4278 return FALSE;
4279 if (!_bfd_vms_write_egsd (abfd))
4280 return FALSE;
4281 if (!_bfd_vms_write_etir (abfd, EOBJ__C_ETIR))
4282 return FALSE;
4283 if (!_bfd_vms_write_eeom (abfd))
4284 return FALSE;
4285 }
95e34ef7
TG
4286 }
4287 return TRUE;
4288}
4289\f
4290/* Debug stuff: nearest line. */
4291
4292#define SET_MODULE_PARSED(m) \
4293 do { if ((m)->name == NULL) (m)->name = ""; } while (0)
4294#define IS_MODULE_PARSED(m) ((m)->name != NULL)
4295
4296/* Build a new module for the specified BFD. */
4297
4298static struct module *
4299new_module (bfd *abfd)
4300{
4301 struct module *module
4302 = (struct module *) bfd_zalloc (abfd, sizeof (struct module));
4303 module->file_table_count = 16; /* Arbitrary. */
4304 module->file_table
4305 = bfd_malloc (module->file_table_count * sizeof (struct fileinfo));
4306 return module;
4307}
4308
4309/* Parse debug info for a module and internalize it. */
4310
9cb56943 4311static bfd_boolean
95e34ef7
TG
4312parse_module (bfd *abfd, struct module *module, unsigned char *ptr,
4313 int length)
4314{
4315 unsigned char *maxptr = ptr + length;
4316 unsigned char *src_ptr, *pcl_ptr;
4317 unsigned int prev_linum = 0, curr_linenum = 0;
4318 bfd_vma prev_pc = 0, curr_pc = 0;
4319 struct srecinfo *curr_srec, *srec;
4320 struct lineinfo *curr_line, *line;
4321 struct funcinfo *funcinfo;
4322
4323 /* Initialize tables with zero element. */
4324 curr_srec = (struct srecinfo *) bfd_zalloc (abfd, sizeof (struct srecinfo));
4325 module->srec_table = curr_srec;
4326
4327 curr_line = (struct lineinfo *) bfd_zalloc (abfd, sizeof (struct lineinfo));
4328 module->line_table = curr_line;
4329
4330 while (length == -1 || ptr < maxptr)
4331 {
4332 /* The first byte is not counted in the recorded length. */
4333 int rec_length = bfd_getl16 (ptr) + 1;
4334 int rec_type = bfd_getl16 (ptr + 2);
4335
4336 vms_debug2 ((2, "DST record: leng %d, type %d\n", rec_length, rec_type));
4337
4338 if (length == -1 && rec_type == DST__K_MODEND)
07d6d2b8 4339 break;
95e34ef7
TG
4340
4341 switch (rec_type)
4342 {
4343 case DST__K_MODBEG:
4344 module->name
37d2e9c7 4345 = _bfd_vms_save_counted_string (abfd, ptr + DST_S_B_MODBEG_NAME,
7adc0a81 4346 maxptr - (ptr + DST_S_B_MODBEG_NAME));
95e34ef7
TG
4347
4348 curr_pc = 0;
4349 prev_pc = 0;
4350 curr_linenum = 0;
4351 prev_linum = 0;
4352
07d6d2b8 4353 vms_debug2 ((3, "module: %s\n", module->name));
95e34ef7
TG
4354 break;
4355
4356 case DST__K_MODEND:
4357 break;
4358
4359 case DST__K_RTNBEG:
4360 funcinfo = (struct funcinfo *)
4361 bfd_zalloc (abfd, sizeof (struct funcinfo));
07d6d2b8 4362 funcinfo->name
37d2e9c7 4363 = _bfd_vms_save_counted_string (abfd, ptr + DST_S_B_RTNBEG_NAME,
7adc0a81 4364 maxptr - (ptr + DST_S_B_RTNBEG_NAME));
95e34ef7
TG
4365 funcinfo->low = bfd_getl32 (ptr + DST_S_L_RTNBEG_ADDRESS);
4366 funcinfo->next = module->func_table;
4367 module->func_table = funcinfo;
4368
07d6d2b8
AM
4369 vms_debug2 ((3, "routine: %s at 0x%lx\n",
4370 funcinfo->name, (unsigned long) funcinfo->low));
95e34ef7
TG
4371 break;
4372
4373 case DST__K_RTNEND:
4374 module->func_table->high = module->func_table->low
4375 + bfd_getl32 (ptr + DST_S_L_RTNEND_SIZE) - 1;
4376
4377 if (module->func_table->high > module->high)
4378 module->high = module->func_table->high;
4379
07d6d2b8 4380 vms_debug2 ((3, "end routine\n"));
95e34ef7
TG
4381 break;
4382
4383 case DST__K_PROLOG:
07d6d2b8 4384 vms_debug2 ((3, "prologue\n"));
95e34ef7
TG
4385 break;
4386
4387 case DST__K_EPILOG:
07d6d2b8 4388 vms_debug2 ((3, "epilog\n"));
95e34ef7
TG
4389 break;
4390
4391 case DST__K_BLKBEG:
07d6d2b8 4392 vms_debug2 ((3, "block\n"));
95e34ef7
TG
4393 break;
4394
4395 case DST__K_BLKEND:
07d6d2b8 4396 vms_debug2 ((3, "end block\n"));
95e34ef7
TG
4397 break;
4398
4399 case DST__K_SOURCE:
4400 src_ptr = ptr + DST_S_C_SOURCE_HEADER_SIZE;
4401
4402 vms_debug2 ((3, "source info\n"));
4403
4404 while (src_ptr < ptr + rec_length)
4405 {
4406 int cmd = src_ptr[0], cmd_length, data;
4407
4408 switch (cmd)
4409 {
4410 case DST__K_SRC_DECLFILE:
4411 {
4412 unsigned int fileid
4413 = bfd_getl16 (src_ptr + DST_S_W_SRC_DF_FILEID);
37d2e9c7
AM
4414 char *filename = _bfd_vms_save_counted_string
4415 (abfd,
4416 src_ptr + DST_S_B_SRC_DF_FILENAME,
4417 ptr + rec_length - (src_ptr + DST_S_B_SRC_DF_FILENAME));
95e34ef7
TG
4418
4419 while (fileid >= module->file_table_count)
4420 {
4421 module->file_table_count *= 2;
4422 module->file_table
9cb56943
AM
4423 = bfd_realloc_or_free (module->file_table,
4424 module->file_table_count
4425 * sizeof (struct fileinfo));
4426 if (module->file_table == NULL)
4427 return FALSE;
95e34ef7
TG
4428 }
4429
4430 module->file_table [fileid].name = filename;
4431 module->file_table [fileid].srec = 1;
4432 cmd_length = src_ptr[DST_S_B_SRC_DF_LENGTH] + 2;
4433 vms_debug2 ((4, "DST_S_C_SRC_DECLFILE: %d, %s\n",
07d6d2b8 4434 fileid, module->file_table [fileid].name));
95e34ef7
TG
4435 }
4436 break;
4437
4438 case DST__K_SRC_DEFLINES_B:
4439 /* Perform the association and set the next higher index
4440 to the limit. */
4441 data = src_ptr[DST_S_B_SRC_UNSBYTE];
4442 srec = (struct srecinfo *)
4443 bfd_zalloc (abfd, sizeof (struct srecinfo));
4444 srec->line = curr_srec->line + data;
4445 srec->srec = curr_srec->srec + data;
4446 srec->sfile = curr_srec->sfile;
4447 curr_srec->next = srec;
4448 curr_srec = srec;
4449 cmd_length = 2;
4450 vms_debug2 ((4, "DST_S_C_SRC_DEFLINES_B: %d\n", data));
4451 break;
4452
4453 case DST__K_SRC_DEFLINES_W:
4454 /* Perform the association and set the next higher index
4455 to the limit. */
4456 data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD);
4457 srec = (struct srecinfo *)
4458 bfd_zalloc (abfd, sizeof (struct srecinfo));
4459 srec->line = curr_srec->line + data;
4460 srec->srec = curr_srec->srec + data,
4461 srec->sfile = curr_srec->sfile;
4462 curr_srec->next = srec;
4463 curr_srec = srec;
4464 cmd_length = 3;
4465 vms_debug2 ((4, "DST_S_C_SRC_DEFLINES_W: %d\n", data));
4466 break;
4467
4468 case DST__K_SRC_INCRLNUM_B:
4469 data = src_ptr[DST_S_B_SRC_UNSBYTE];
4470 curr_srec->line += data;
4471 cmd_length = 2;
4472 vms_debug2 ((4, "DST_S_C_SRC_INCRLNUM_B: %d\n", data));
4473 break;
4474
4475 case DST__K_SRC_SETFILE:
4476 data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD);
4477 curr_srec->sfile = data;
4478 curr_srec->srec = module->file_table[data].srec;
4479 cmd_length = 3;
4480 vms_debug2 ((4, "DST_S_C_SRC_SETFILE: %d\n", data));
4481 break;
4482
4483 case DST__K_SRC_SETLNUM_L:
4484 data = bfd_getl32 (src_ptr + DST_S_L_SRC_UNSLONG);
4485 curr_srec->line = data;
4486 cmd_length = 5;
4487 vms_debug2 ((4, "DST_S_C_SRC_SETLNUM_L: %d\n", data));
4488 break;
4489
4490 case DST__K_SRC_SETLNUM_W:
4491 data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD);
4492 curr_srec->line = data;
4493 cmd_length = 3;
4494 vms_debug2 ((4, "DST_S_C_SRC_SETLNUM_W: %d\n", data));
4495 break;
4496
4497 case DST__K_SRC_SETREC_L:
4498 data = bfd_getl32 (src_ptr + DST_S_L_SRC_UNSLONG);
4499 curr_srec->srec = data;
4500 module->file_table[curr_srec->sfile].srec = data;
4501 cmd_length = 5;
4502 vms_debug2 ((4, "DST_S_C_SRC_SETREC_L: %d\n", data));
4503 break;
4504
4505 case DST__K_SRC_SETREC_W:
4506 data = bfd_getl16 (src_ptr + DST_S_W_SRC_UNSWORD);
4507 curr_srec->srec = data;
4508 module->file_table[curr_srec->sfile].srec = data;
4509 cmd_length = 3;
4510 vms_debug2 ((4, "DST_S_C_SRC_SETREC_W: %d\n", data));
4511 break;
4512
4513 case DST__K_SRC_FORMFEED:
4514 cmd_length = 1;
4515 vms_debug2 ((4, "DST_S_C_SRC_FORMFEED\n"));
4516 break;
4517
4518 default:
4eca0228
AM
4519 _bfd_error_handler (_("unknown source command %d"),
4520 cmd);
95e34ef7
TG
4521 cmd_length = 2;
4522 break;
4523 }
4524
4525 src_ptr += cmd_length;
4526 }
4527 break;
4528
4529 case DST__K_LINE_NUM:
4530 pcl_ptr = ptr + DST_S_C_LINE_NUM_HEADER_SIZE;
4531
4532 vms_debug2 ((3, "line info\n"));
4533
4534 while (pcl_ptr < ptr + rec_length)
4535 {
4536 /* The command byte is signed so we must sign-extend it. */
4537 int cmd = ((signed char *)pcl_ptr)[0], cmd_length, data;
4538
4539 switch (cmd)
4540 {
4541 case DST__K_DELTA_PC_W:
4542 data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD);
4543 curr_pc += data;
4544 curr_linenum += 1;
4545 cmd_length = 3;
4546 vms_debug2 ((4, "DST__K_DELTA_PC_W: %d\n", data));
4547 break;
4548
4549 case DST__K_DELTA_PC_L:
4550 data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG);
4551 curr_pc += data;
4552 curr_linenum += 1;
4553 cmd_length = 5;
4554 vms_debug2 ((4, "DST__K_DELTA_PC_L: %d\n", data));
4555 break;
4556
4557 case DST__K_INCR_LINUM:
4558 data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE];
4559 curr_linenum += data;
4560 cmd_length = 2;
4561 vms_debug2 ((4, "DST__K_INCR_LINUM: %d\n", data));
4562 break;
4563
4564 case DST__K_INCR_LINUM_W:
4565 data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD);
4566 curr_linenum += data;
4567 cmd_length = 3;
4568 vms_debug2 ((4, "DST__K_INCR_LINUM_W: %d\n", data));
4569 break;
4570
4571 case DST__K_INCR_LINUM_L:
4572 data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG);
4573 curr_linenum += data;
4574 cmd_length = 5;
4575 vms_debug2 ((4, "DST__K_INCR_LINUM_L: %d\n", data));
4576 break;
4577
4578 case DST__K_SET_LINUM_INCR:
4eca0228 4579 _bfd_error_handler
38f14ab8 4580 (_("%s not implemented"), "DST__K_SET_LINUM_INCR");
95e34ef7
TG
4581 cmd_length = 2;
4582 break;
4583
4584 case DST__K_SET_LINUM_INCR_W:
4eca0228 4585 _bfd_error_handler
38f14ab8 4586 (_("%s not implemented"), "DST__K_SET_LINUM_INCR_W");
95e34ef7
TG
4587 cmd_length = 3;
4588 break;
4589
4590 case DST__K_RESET_LINUM_INCR:
4eca0228 4591 _bfd_error_handler
38f14ab8 4592 (_("%s not implemented"), "DST__K_RESET_LINUM_INCR");
95e34ef7
TG
4593 cmd_length = 1;
4594 break;
4595
4596 case DST__K_BEG_STMT_MODE:
4eca0228 4597 _bfd_error_handler
38f14ab8 4598 (_("%s not implemented"), "DST__K_BEG_STMT_MODE");
95e34ef7
TG
4599 cmd_length = 1;
4600 break;
4601
4602 case DST__K_END_STMT_MODE:
4eca0228 4603 _bfd_error_handler
38f14ab8 4604 (_("%s not implemented"), "DST__K_END_STMT_MODE");
95e34ef7
TG
4605 cmd_length = 1;
4606 break;
4607
4608 case DST__K_SET_LINUM_B:
4609 data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE];
4610 curr_linenum = data;
4611 cmd_length = 2;
4612 vms_debug2 ((4, "DST__K_SET_LINUM_B: %d\n", data));
4613 break;
4614
4615 case DST__K_SET_LINUM:
4616 data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD);
4617 curr_linenum = data;
4618 cmd_length = 3;
4619 vms_debug2 ((4, "DST__K_SET_LINE_NUM: %d\n", data));
4620 break;
4621
4622 case DST__K_SET_LINUM_L:
4623 data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG);
4624 curr_linenum = data;
4625 cmd_length = 5;
4626 vms_debug2 ((4, "DST__K_SET_LINUM_L: %d\n", data));
4627 break;
4628
4629 case DST__K_SET_PC:
4eca0228 4630 _bfd_error_handler
38f14ab8 4631 (_("%s not implemented"), "DST__K_SET_PC");
95e34ef7
TG
4632 cmd_length = 2;
4633 break;
4634
4635 case DST__K_SET_PC_W:
4eca0228 4636 _bfd_error_handler
38f14ab8 4637 (_("%s not implemented"), "DST__K_SET_PC_W");
95e34ef7
TG
4638 cmd_length = 3;
4639 break;
4640
4641 case DST__K_SET_PC_L:
4eca0228 4642 _bfd_error_handler
38f14ab8 4643 (_("%s not implemented"), "DST__K_SET_PC_L");
95e34ef7
TG
4644 cmd_length = 5;
4645 break;
4646
4647 case DST__K_SET_STMTNUM:
4eca0228 4648 _bfd_error_handler
38f14ab8 4649 (_("%s not implemented"), "DST__K_SET_STMTNUM");
95e34ef7
TG
4650 cmd_length = 2;
4651 break;
4652
4653 case DST__K_TERM:
4654 data = pcl_ptr[DST_S_B_PCLINE_UNSBYTE];
4655 curr_pc += data;
4656 cmd_length = 2;
4657 vms_debug2 ((4, "DST__K_TERM: %d\n", data));
4658 break;
4659
4660 case DST__K_TERM_W:
4661 data = bfd_getl16 (pcl_ptr + DST_S_W_PCLINE_UNSWORD);
4662 curr_pc += data;
4663 cmd_length = 3;
4664 vms_debug2 ((4, "DST__K_TERM_W: %d\n", data));
4665 break;
4666
4667 case DST__K_TERM_L:
4668 data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG);
4669 curr_pc += data;
4670 cmd_length = 5;
4671 vms_debug2 ((4, "DST__K_TERM_L: %d\n", data));
4672 break;
4673
4674 case DST__K_SET_ABS_PC:
4675 data = bfd_getl32 (pcl_ptr + DST_S_L_PCLINE_UNSLONG);
4676 curr_pc = data;
4677 cmd_length = 5;
4678 vms_debug2 ((4, "DST__K_SET_ABS_PC: 0x%x\n", data));
4679 break;
4680
4681 default:
4682 if (cmd <= 0)
4683 {
4684 curr_pc -= cmd;
4685 curr_linenum += 1;
4686 cmd_length = 1;
4687 vms_debug2 ((4, "bump pc to 0x%lx and line to %d\n",
07d6d2b8 4688 (unsigned long)curr_pc, curr_linenum));
95e34ef7
TG
4689 }
4690 else
4691 {
4eca0228 4692 _bfd_error_handler (_("unknown line command %d"), cmd);
95e34ef7
TG
4693 cmd_length = 2;
4694 }
4695 break;
4696 }
4697
4698 if ((curr_linenum != prev_linum && curr_pc != prev_pc)
4699 || cmd <= 0
4700 || cmd == DST__K_DELTA_PC_L
4701 || cmd == DST__K_DELTA_PC_W)
4702 {
4703 line = (struct lineinfo *)
4704 bfd_zalloc (abfd, sizeof (struct lineinfo));
4705 line->address = curr_pc;
4706 line->line = curr_linenum;
4707
4708 curr_line->next = line;
4709 curr_line = line;
4710
4711 prev_linum = curr_linenum;
4712 prev_pc = curr_pc;
4713 vms_debug2 ((4, "-> correlate pc 0x%lx with line %d\n",
07d6d2b8 4714 (unsigned long)curr_pc, curr_linenum));
95e34ef7
TG
4715 }
4716
4717 pcl_ptr += cmd_length;
4718 }
4719 break;
4720
4721 case 0x17: /* Undocumented type used by DEC C to declare equates. */
4722 vms_debug2 ((3, "undocumented type 0x17\n"));
4723 break;
4724
4725 default:
4726 vms_debug2 ((3, "ignoring record\n"));
4727 break;
4728
4729 }
4730
4731 ptr += rec_length;
4732 }
4733
4734 /* Finalize tables with EOL marker. */
4735 srec = (struct srecinfo *) bfd_zalloc (abfd, sizeof (struct srecinfo));
4736 srec->line = (unsigned int) -1;
4737 srec->srec = (unsigned int) -1;
4738 curr_srec->next = srec;
4739
4740 line = (struct lineinfo *) bfd_zalloc (abfd, sizeof (struct lineinfo));
4741 line->line = (unsigned int) -1;
4742 line->address = (bfd_vma) -1;
4743 curr_line->next = line;
4744
4745 /* Advertise that this module has been parsed. This is needed
4746 because parsing can be either performed at module creation
4747 or deferred until debug info is consumed. */
4748 SET_MODULE_PARSED (module);
9cb56943 4749 return TRUE;
95e34ef7
TG
4750}
4751
4752/* Build the list of modules for the specified BFD. */
4753
4754static struct module *
4755build_module_list (bfd *abfd)
4756{
4757 struct module *module, *list = NULL;
4758 asection *dmt;
4759
4760 if ((dmt = bfd_get_section_by_name (abfd, "$DMT$")))
4761 {
4762 /* We have a DMT section so this must be an image. Parse the
4763 section and build the list of modules. This is sufficient
4764 since we can compute the start address and the end address
4765 of every module from the section contents. */
fd361982 4766 bfd_size_type size = bfd_section_size (dmt);
95e34ef7
TG
4767 unsigned char *ptr, *end;
4768
4769 ptr = (unsigned char *) bfd_alloc (abfd, size);
4770 if (! ptr)
4771 return NULL;
4772
4773 if (! bfd_get_section_contents (abfd, dmt, ptr, 0, size))
4774 return NULL;
4775
4776 vms_debug2 ((2, "DMT\n"));
4777
4778 end = ptr + size;
4779
4780 while (ptr < end)
4781 {
4782 /* Each header declares a module with its start offset and size
4783 of debug info in the DST section, as well as the count of
4784 program sections (i.e. address spans) it contains. */
4785 int modbeg = bfd_getl32 (ptr + DBG_S_L_DMT_MODBEG);
4786 int msize = bfd_getl32 (ptr + DBG_S_L_DST_SIZE);
4787 int count = bfd_getl16 (ptr + DBG_S_W_DMT_PSECT_COUNT);
4788 ptr += DBG_S_C_DMT_HEADER_SIZE;
4789
4790 vms_debug2 ((3, "module: modbeg = %d, size = %d, count = %d\n",
07d6d2b8 4791 modbeg, msize, count));
95e34ef7
TG
4792
4793 /* We create a 'module' structure for each program section since
4794 we only support contiguous addresses in a 'module' structure.
4795 As a consequence, the actual debug info in the DST section is
4796 shared and can be parsed multiple times; that doesn't seem to
4797 cause problems in practice. */
4798 while (count-- > 0)
4799 {
4800 int start = bfd_getl32 (ptr + DBG_S_L_DMT_PSECT_START);
4801 int length = bfd_getl32 (ptr + DBG_S_L_DMT_PSECT_LENGTH);
4802 module = new_module (abfd);
4803 module->modbeg = modbeg;
4804 module->size = msize;
4805 module->low = start;
4806 module->high = start + length;
4807 module->next = list;
4808 list = module;
4809 ptr += DBG_S_C_DMT_PSECT_SIZE;
4810
4811 vms_debug2 ((4, "section: start = 0x%x, length = %d\n",
07d6d2b8 4812 start, length));
95e34ef7
TG
4813 }
4814 }
4815 }
4816 else
4817 {
4818 /* We don't have a DMT section so this must be an object. Parse
4819 the module right now in order to compute its start address and
4820 end address. */
8185f55c
TG
4821 void *dst = PRIV (dst_section)->contents;
4822
4823 if (dst == NULL)
07d6d2b8 4824 return NULL;
8185f55c 4825
95e34ef7 4826 module = new_module (abfd);
9cb56943
AM
4827 if (!parse_module (abfd, module, PRIV (dst_section)->contents, -1))
4828 return NULL;
95e34ef7
TG
4829 list = module;
4830 }
4831
4832 return list;
4833}
4834
4835/* Calculate and return the name of the source file and the line nearest
4836 to the wanted location in the specified module. */
4837
4838static bfd_boolean
4839module_find_nearest_line (bfd *abfd, struct module *module, bfd_vma addr,
4840 const char **file, const char **func,
4841 unsigned int *line)
4842{
4843 struct funcinfo *funcinfo;
4844 struct lineinfo *lineinfo;
4845 struct srecinfo *srecinfo;
4846 bfd_boolean ret = FALSE;
4847
4848 /* Parse this module if that was not done at module creation. */
4849 if (! IS_MODULE_PARSED (module))
4850 {
4851 unsigned int size = module->size;
4852 unsigned int modbeg = PRIV (dst_section)->filepos + module->modbeg;
2bb3687b 4853 unsigned char *buffer;
95e34ef7
TG
4854
4855 if (bfd_seek (abfd, modbeg, SEEK_SET) != 0
2bb3687b 4856 || (buffer = _bfd_malloc_and_read (abfd, size, size)) == NULL)
95e34ef7
TG
4857 {
4858 bfd_set_error (bfd_error_no_debug_section);
4859 return FALSE;
4860 }
4861
9cb56943 4862 ret = parse_module (abfd, module, buffer, size);
95e34ef7 4863 free (buffer);
9cb56943
AM
4864 if (!ret)
4865 return ret;
95e34ef7
TG
4866 }
4867
4868 /* Find out the function (if any) that contains the address. */
4869 for (funcinfo = module->func_table; funcinfo; funcinfo = funcinfo->next)
4870 if (addr >= funcinfo->low && addr <= funcinfo->high)
4871 {
07d6d2b8 4872 *func = funcinfo->name;
95e34ef7
TG
4873 ret = TRUE;
4874 break;
4875 }
4876
4877 /* Find out the source file and the line nearest to the address. */
4878 for (lineinfo = module->line_table; lineinfo; lineinfo = lineinfo->next)
4879 if (lineinfo->next && addr < lineinfo->next->address)
4880 {
4881 for (srecinfo = module->srec_table; srecinfo; srecinfo = srecinfo->next)
4882 if (srecinfo->next && lineinfo->line < srecinfo->next->line)
4883 {
4884 if (srecinfo->sfile > 0)
4885 {
4886 *file = module->file_table[srecinfo->sfile].name;
4887 *line = srecinfo->srec + lineinfo->line - srecinfo->line;
4888 }
4889 else
4890 {
4891 *file = module->name;
4892 *line = lineinfo->line;
4893 }
4894 return TRUE;
4895 }
4896
4897 break;
4898 }
4899
4900 return ret;
4901}
4902
4903/* Provided a BFD, a section and an offset into the section, calculate and
4904 return the name of the source file and the line nearest to the wanted
4905 location. */
4906
4907static bfd_boolean
fb167eb2
AM
4908_bfd_vms_find_nearest_line (bfd *abfd,
4909 asymbol **symbols ATTRIBUTE_UNUSED,
4910 asection *section,
4911 bfd_vma offset,
4912 const char **file,
4913 const char **func,
4914 unsigned int *line,
4915 unsigned int *discriminator)
95e34ef7
TG
4916{
4917 struct module *module;
4918
4919 /* What address are we looking for? */
4920 bfd_vma addr = section->vma + offset;
4921
4922 *file = NULL;
4923 *func = NULL;
4924 *line = 0;
fb167eb2
AM
4925 if (discriminator)
4926 *discriminator = 0;
95e34ef7 4927
8185f55c 4928 /* We can't do anything if there is no DST (debug symbol table). */
a283ff93 4929 if (PRIV (dst_section) == NULL)
95e34ef7
TG
4930 return FALSE;
4931
8185f55c 4932 /* Create the module list - if not already done. */
95e34ef7
TG
4933 if (PRIV (modules) == NULL)
4934 {
4935 PRIV (modules) = build_module_list (abfd);
4936 if (PRIV (modules) == NULL)
07d6d2b8 4937 return FALSE;
95e34ef7
TG
4938 }
4939
4940 for (module = PRIV (modules); module; module = module->next)
4941 if (addr >= module->low && addr <= module->high)
4942 return module_find_nearest_line (abfd, module, addr, file, func, line);
4943
4944 return FALSE;
4945}
4946\f
4947/* Canonicalizations. */
4948/* Set name, value, section and flags of SYM from E. */
4949
4950static bfd_boolean
4951alpha_vms_convert_symbol (bfd *abfd, struct vms_symbol_entry *e, asymbol *sym)
4952{
4953 flagword flags;
4954 symvalue value;
4955 asection *sec;
4956 const char *name;
4957
4958 name = e->name;
4959 value = 0;
4960 flags = BSF_NO_FLAGS;
4961 sec = NULL;
4962
4963 switch (e->typ)
4964 {
4965 case EGSD__C_SYM:
4966 if (e->flags & EGSY__V_WEAK)
07d6d2b8 4967 flags |= BSF_WEAK;
95e34ef7
TG
4968
4969 if (e->flags & EGSY__V_DEF)
07d6d2b8
AM
4970 {
4971 /* Symbol definition. */
4972 flags |= BSF_GLOBAL;
4973 if (e->flags & EGSY__V_NORM)
4974 flags |= BSF_FUNCTION;
4975 value = e->value;
4976 sec = e->section;
4977 }
95e34ef7 4978 else
07d6d2b8
AM
4979 {
4980 /* Symbol reference. */
4981 sec = bfd_und_section_ptr;
4982 }
95e34ef7
TG
4983 break;
4984
4985 case EGSD__C_SYMG:
4986 /* A universal symbol is by definition global... */
4987 flags |= BSF_GLOBAL;
4988
4989 /* ...and dynamic in shared libraries. */
4990 if (abfd->flags & DYNAMIC)
07d6d2b8 4991 flags |= BSF_DYNAMIC;
95e34ef7
TG
4992
4993 if (e->flags & EGSY__V_WEAK)
07d6d2b8 4994 flags |= BSF_WEAK;
95e34ef7
TG
4995
4996 if (!(e->flags & EGSY__V_DEF))
07d6d2b8 4997 abort ();
95e34ef7
TG
4998
4999 if (e->flags & EGSY__V_NORM)
07d6d2b8 5000 flags |= BSF_FUNCTION;
95e34ef7 5001
a928f1d7
TG
5002 value = e->value;
5003 /* sec = e->section; */
95e34ef7 5004 sec = bfd_abs_section_ptr;
95e34ef7
TG
5005 break;
5006
5007 default:
5008 return FALSE;
5009 }
5010
5011 sym->name = name;
5012 sym->section = sec;
5013 sym->flags = flags;
5014 sym->value = value;
5015 return TRUE;
5016}
5017
5018
5019/* Return the number of bytes required to store a vector of pointers
5020 to asymbols for all the symbols in the BFD abfd, including a
5021 terminal NULL pointer. If there are no symbols in the BFD,
5022 then return 0. If an error occurs, return -1. */
5023
5024static long
5025alpha_vms_get_symtab_upper_bound (bfd *abfd)
5026{
5027 vms_debug2 ((1, "alpha_vms_get_symtab_upper_bound (%p), %d symbols\n",
07d6d2b8 5028 abfd, PRIV (gsd_sym_count)));
95e34ef7
TG
5029
5030 return (PRIV (gsd_sym_count) + 1) * sizeof (asymbol *);
5031}
5032
5033/* Read the symbols from the BFD abfd, and fills in the vector
5034 location with pointers to the symbols and a trailing NULL.
5035
5036 Return number of symbols read. */
5037
5038static long
5039alpha_vms_canonicalize_symtab (bfd *abfd, asymbol **symbols)
5040{
5041 unsigned int i;
5042
5043 vms_debug2 ((1, "alpha_vms_canonicalize_symtab (%p, <ret>)\n", abfd));
5044
5045 if (PRIV (csymbols) == NULL)
5046 {
5047 PRIV (csymbols) = (asymbol **) bfd_alloc
07d6d2b8 5048 (abfd, PRIV (gsd_sym_count) * sizeof (asymbol *));
95e34ef7
TG
5049
5050 /* Traverse table and fill symbols vector. */
5051 for (i = 0; i < PRIV (gsd_sym_count); i++)
07d6d2b8
AM
5052 {
5053 struct vms_symbol_entry *e = PRIV (syms)[i];
5054 asymbol *sym;
95e34ef7 5055
07d6d2b8
AM
5056 sym = bfd_make_empty_symbol (abfd);
5057 if (sym == NULL || !alpha_vms_convert_symbol (abfd, e, sym))
5058 {
5059 bfd_release (abfd, PRIV (csymbols));
5060 PRIV (csymbols) = NULL;
5061 return -1;
5062 }
95e34ef7 5063
07d6d2b8
AM
5064 PRIV (csymbols)[i] = sym;
5065 }
95e34ef7
TG
5066 }
5067
5068 if (symbols != NULL)
5069 {
5070 for (i = 0; i < PRIV (gsd_sym_count); i++)
07d6d2b8 5071 symbols[i] = PRIV (csymbols)[i];
95e34ef7
TG
5072 symbols[i] = NULL;
5073 }
5074
5075 return PRIV (gsd_sym_count);
5076}
5077
5078/* Read and convert relocations from ETIR. We do it once for all sections. */
5079
5080static bfd_boolean
5081alpha_vms_slurp_relocs (bfd *abfd)
5082{
5083 int cur_psect = -1;
5084
5085 vms_debug2 ((3, "alpha_vms_slurp_relocs\n"));
5086
5087 /* We slurp relocs only once, for all sections. */
5088 if (PRIV (reloc_done))
5089 return TRUE;
5090 PRIV (reloc_done) = TRUE;
5091
5092 if (alpha_vms_canonicalize_symtab (abfd, NULL) < 0)
5093 return FALSE;
5094
5095 if (bfd_seek (abfd, 0, SEEK_SET) != 0)
5096 return FALSE;
5097
5098 while (1)
5099 {
5100 unsigned char *begin;
5101 unsigned char *end;
5102 unsigned char *ptr;
5103 bfd_reloc_code_real_type reloc_code;
5104 int type;
5105 bfd_vma vaddr = 0;
5106
5107 int length;
5108
5109 bfd_vma cur_address;
5110 int cur_psidx = -1;
5111 unsigned char *cur_sym = NULL;
5112 int prev_cmd = -1;
5113 bfd_vma cur_addend = 0;
5114
5115 /* Skip non-ETIR records. */
5116 type = _bfd_vms_get_object_record (abfd);
5117 if (type == EOBJ__C_EEOM)
07d6d2b8 5118 break;
95e34ef7 5119 if (type != EOBJ__C_ETIR)
07d6d2b8 5120 continue;
95e34ef7
TG
5121
5122 begin = PRIV (recrd.rec) + 4;
5123 end = PRIV (recrd.rec) + PRIV (recrd.rec_size);
5124
5125 for (ptr = begin; ptr < end; ptr += length)
07d6d2b8
AM
5126 {
5127 int cmd;
5128
5129 cmd = bfd_getl16 (ptr);
5130 length = bfd_getl16 (ptr + 2);
5131
5132 cur_address = vaddr;
5133
5134 vms_debug2 ((4, "alpha_vms_slurp_relocs: etir %s\n",
5135 _bfd_vms_etir_name (cmd)));
5136
5137 switch (cmd)
5138 {
5139 case ETIR__C_STA_GBL: /* ALPHA_R_REFLONG und_section, step 1 */
5140 /* ALPHA_R_REFQUAD und_section, step 1 */
5141 cur_sym = ptr + 4;
5142 prev_cmd = cmd;
5143 continue;
5144
5145 case ETIR__C_STA_PQ: /* ALPHA_R_REF{LONG|QUAD}, others part 1 */
5146 cur_psidx = bfd_getl32 (ptr + 4);
5147 cur_addend = bfd_getl64 (ptr + 8);
5148 prev_cmd = cmd;
5149 continue;
5150
5151 case ETIR__C_CTL_SETRB:
5152 if (prev_cmd != ETIR__C_STA_PQ)
5153 {
4eca0228 5154 _bfd_error_handler
695344c0 5155 /* xgettext:c-format */
38f14ab8 5156 (_("unknown reloc %s + %s"), _bfd_vms_etir_name (prev_cmd),
07d6d2b8
AM
5157 _bfd_vms_etir_name (cmd));
5158 return FALSE;
5159 }
5160 cur_psect = cur_psidx;
5161 vaddr = cur_addend;
5162 cur_psidx = -1;
5163 cur_addend = 0;
5164 continue;
5165
5166 case ETIR__C_STA_LW: /* ALPHA_R_REFLONG abs_section, step 1 */
5167 /* ALPHA_R_REFLONG und_section, step 2 */
5168 if (prev_cmd != -1)
5169 {
5170 if (prev_cmd != ETIR__C_STA_GBL)
5171 {
4eca0228 5172 _bfd_error_handler
695344c0 5173 /* xgettext:c-format */
38f14ab8 5174 (_("unknown reloc %s + %s"), _bfd_vms_etir_name (cmd),
07d6d2b8
AM
5175 _bfd_vms_etir_name (ETIR__C_STA_LW));
5176 return FALSE;
5177 }
5178 }
5179 cur_addend = bfd_getl32 (ptr + 4);
5180 prev_cmd = cmd;
5181 continue;
5182
5183 case ETIR__C_STA_QW: /* ALPHA_R_REFQUAD abs_section, step 1 */
5184 /* ALPHA_R_REFQUAD und_section, step 2 */
5185 if (prev_cmd != -1 && prev_cmd != ETIR__C_STA_GBL)
5186 {
4eca0228 5187 _bfd_error_handler
695344c0 5188 /* xgettext:c-format */
38f14ab8 5189 (_("unknown reloc %s + %s"), _bfd_vms_etir_name (cmd),
07d6d2b8
AM
5190 _bfd_vms_etir_name (ETIR__C_STA_QW));
5191 return FALSE;
5192 }
5193 cur_addend = bfd_getl64 (ptr + 4);
5194 prev_cmd = cmd;
5195 continue;
5196
5197 case ETIR__C_STO_LW: /* ALPHA_R_REFLONG und_section, step 4 */
5198 /* ALPHA_R_REFLONG abs_section, step 2 */
5199 /* ALPHA_R_REFLONG others, step 2 */
5200 if (prev_cmd != ETIR__C_OPR_ADD
5201 && prev_cmd != ETIR__C_STA_LW
5202 && prev_cmd != ETIR__C_STA_PQ)
5203 {
695344c0 5204 /* xgettext:c-format */
38f14ab8 5205 _bfd_error_handler (_("unknown reloc %s + %s"),
4eca0228
AM
5206 _bfd_vms_etir_name (prev_cmd),
5207 _bfd_vms_etir_name (ETIR__C_STO_LW));
07d6d2b8
AM
5208 return FALSE;
5209 }
5210 reloc_code = BFD_RELOC_32;
5211 break;
5212
5213 case ETIR__C_STO_QW: /* ALPHA_R_REFQUAD und_section, step 4 */
5214 /* ALPHA_R_REFQUAD abs_section, step 2 */
5215 if (prev_cmd != ETIR__C_OPR_ADD && prev_cmd != ETIR__C_STA_QW)
5216 {
695344c0 5217 /* xgettext:c-format */
38f14ab8 5218 _bfd_error_handler (_("unknown reloc %s + %s"),
4eca0228
AM
5219 _bfd_vms_etir_name (prev_cmd),
5220 _bfd_vms_etir_name (ETIR__C_STO_QW));
07d6d2b8
AM
5221 return FALSE;
5222 }
5223 reloc_code = BFD_RELOC_64;
5224 break;
5225
5226 case ETIR__C_STO_OFF: /* ALPHA_R_REFQUAD others, step 2 */
5227 if (prev_cmd != ETIR__C_STA_PQ)
5228 {
695344c0 5229 /* xgettext:c-format */
38f14ab8 5230 _bfd_error_handler (_("unknown reloc %s + %s"),
4eca0228
AM
5231 _bfd_vms_etir_name (prev_cmd),
5232 _bfd_vms_etir_name (ETIR__C_STO_OFF));
07d6d2b8
AM
5233 return FALSE;
5234 }
5235 reloc_code = BFD_RELOC_64;
5236 break;
5237
5238 case ETIR__C_OPR_ADD: /* ALPHA_R_REFLONG und_section, step 3 */
5239 /* ALPHA_R_REFQUAD und_section, step 3 */
5240 if (prev_cmd != ETIR__C_STA_LW && prev_cmd != ETIR__C_STA_QW)
5241 {
695344c0 5242 /* xgettext:c-format */
38f14ab8 5243 _bfd_error_handler (_("unknown reloc %s + %s"),
4eca0228
AM
5244 _bfd_vms_etir_name (prev_cmd),
5245 _bfd_vms_etir_name (ETIR__C_OPR_ADD));
07d6d2b8
AM
5246 return FALSE;
5247 }
5248 prev_cmd = ETIR__C_OPR_ADD;
5249 continue;
5250
5251 case ETIR__C_STO_CA: /* ALPHA_R_CODEADDR */
5252 reloc_code = BFD_RELOC_ALPHA_CODEADDR;
5253 cur_sym = ptr + 4;
5254 break;
5255
5256 case ETIR__C_STO_GBL: /* ALPHA_R_REFQUAD und_section */
5257 reloc_code = BFD_RELOC_64;
5258 cur_sym = ptr + 4;
5259 break;
5260
5261 case ETIR__C_STO_GBL_LW: /* ALPHA_R_REFLONG und_section */
5262 reloc_code = BFD_RELOC_32;
5263 cur_sym = ptr + 4;
5264 break;
5265
5266 case ETIR__C_STC_LP_PSB: /* ALPHA_R_LINKAGE */
5267 reloc_code = BFD_RELOC_ALPHA_LINKAGE;
5268 cur_sym = ptr + 8;
5269 break;
5270
5271 case ETIR__C_STC_NOP_GBL: /* ALPHA_R_NOP */
5272 reloc_code = BFD_RELOC_ALPHA_NOP;
5273 goto call_reloc;
5274
5275 case ETIR__C_STC_BSR_GBL: /* ALPHA_R_BSR */
5276 reloc_code = BFD_RELOC_ALPHA_BSR;
5277 goto call_reloc;
5278
5279 case ETIR__C_STC_LDA_GBL: /* ALPHA_R_LDA */
5280 reloc_code = BFD_RELOC_ALPHA_LDA;
5281 goto call_reloc;
5282
5283 case ETIR__C_STC_BOH_GBL: /* ALPHA_R_BOH */
5284 reloc_code = BFD_RELOC_ALPHA_BOH;
5285 goto call_reloc;
5286
5287 call_reloc:
5288 cur_sym = ptr + 4 + 32;
5289 cur_address = bfd_getl64 (ptr + 4 + 8);
5290 cur_addend = bfd_getl64 (ptr + 4 + 24);
5291 break;
5292
5293 case ETIR__C_STO_IMM:
5294 vaddr += bfd_getl32 (ptr + 4);
5295 continue;
5296
5297 default:
38f14ab8 5298 _bfd_error_handler (_("unknown reloc %s"),
4eca0228 5299 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
5300 return FALSE;
5301 }
95e34ef7 5302
07d6d2b8
AM
5303 {
5304 asection *sec;
5305 struct vms_section_data_struct *vms_sec;
5306 arelent *reloc;
706704c8 5307 bfd_size_type size;
95e34ef7 5308
07d6d2b8
AM
5309 /* Get section to which the relocation applies. */
5310 if (cur_psect < 0 || cur_psect > (int)PRIV (section_count))
5311 {
38f14ab8 5312 _bfd_error_handler (_("invalid section index in ETIR"));
07d6d2b8
AM
5313 return FALSE;
5314 }
d120eec2 5315
cb06d03a
NC
5316 if (PRIV (sections) == NULL)
5317 return FALSE;
07d6d2b8
AM
5318 sec = PRIV (sections)[cur_psect];
5319 if (sec == bfd_abs_section_ptr)
5320 {
38f14ab8 5321 _bfd_error_handler (_("relocation for non-REL psect"));
07d6d2b8
AM
5322 return FALSE;
5323 }
5324
5325 vms_sec = vms_section_data (sec);
5326
5327 /* Allocate a reloc entry. */
5328 if (sec->reloc_count >= vms_sec->reloc_max)
5329 {
5330 if (vms_sec->reloc_max == 0)
5331 {
5332 vms_sec->reloc_max = 64;
5333 sec->relocation = bfd_zmalloc
5334 (vms_sec->reloc_max * sizeof (arelent));
5335 }
5336 else
5337 {
5338 vms_sec->reloc_max *= 2;
9cb56943 5339 sec->relocation = bfd_realloc_or_free
07d6d2b8 5340 (sec->relocation, vms_sec->reloc_max * sizeof (arelent));
9cb56943
AM
5341 if (sec->relocation == NULL)
5342 return FALSE;
07d6d2b8
AM
5343 }
5344 }
5345 reloc = &sec->relocation[sec->reloc_count];
5346 sec->reloc_count++;
5347
5348 reloc->howto = bfd_reloc_type_lookup (abfd, reloc_code);
5349
5350 if (cur_sym != NULL)
5351 {
5352 unsigned int j;
5353 unsigned int symlen = *cur_sym;
5354 asymbol **sym;
5355
5356 /* Linear search. */
5357 symlen = *cur_sym;
5358 cur_sym++;
5359 sym = NULL;
5360
5361 for (j = 0; j < PRIV (gsd_sym_count); j++)
5362 if (PRIV (syms)[j]->namelen == symlen
5363 && memcmp (PRIV (syms)[j]->name, cur_sym, symlen) == 0)
5364 {
5365 sym = &PRIV (csymbols)[j];
5366 break;
5367 }
5368 if (sym == NULL)
5369 {
38f14ab8 5370 _bfd_error_handler (_("unknown symbol in command %s"),
4eca0228 5371 _bfd_vms_etir_name (cmd));
07d6d2b8
AM
5372 reloc->sym_ptr_ptr = NULL;
5373 }
5374 else
5375 reloc->sym_ptr_ptr = sym;
5376 }
5377 else if (cur_psidx >= 0)
cb06d03a 5378 {
ca4cf9b9 5379 if (PRIV (sections) == NULL || cur_psidx >= (int) PRIV (section_count))
cb06d03a
NC
5380 return FALSE;
5381 reloc->sym_ptr_ptr =
5382 PRIV (sections)[cur_psidx]->symbol_ptr_ptr;
5383 }
07d6d2b8
AM
5384 else
5385 reloc->sym_ptr_ptr = NULL;
95e34ef7 5386
07d6d2b8
AM
5387 reloc->address = cur_address;
5388 reloc->addend = cur_addend;
95e34ef7 5389
706704c8
AM
5390 if (reloc_code == ALPHA_R_LINKAGE)
5391 size = 16;
5392 else
5393 size = bfd_get_reloc_size (reloc->howto);
5394 vaddr += size;
07d6d2b8 5395 }
95e34ef7 5396
07d6d2b8
AM
5397 cur_addend = 0;
5398 prev_cmd = -1;
5399 cur_sym = NULL;
5400 cur_psidx = -1;
5401 }
95e34ef7
TG
5402 }
5403 vms_debug2 ((3, "alpha_vms_slurp_relocs: result = TRUE\n"));
5404
5405 return TRUE;
5406}
5407
5408/* Return the number of bytes required to store the relocation
5409 information associated with the given section. */
5410
5411static long
5412alpha_vms_get_reloc_upper_bound (bfd *abfd ATTRIBUTE_UNUSED, asection *section)
5413{
5414 alpha_vms_slurp_relocs (abfd);
5415
5416 return (section->reloc_count + 1) * sizeof (arelent *);
5417}
5418
5419/* Convert relocations from VMS (external) form into BFD internal
5420 form. Return the number of relocations. */
5421
5422static long
5423alpha_vms_canonicalize_reloc (bfd *abfd, asection *section, arelent **relptr,
07d6d2b8 5424 asymbol **symbols ATTRIBUTE_UNUSED)
95e34ef7
TG
5425{
5426 arelent *tblptr;
5427 int count;
5428
5429 if (!alpha_vms_slurp_relocs (abfd))
5430 return -1;
5431
5432 count = section->reloc_count;
5433 tblptr = section->relocation;
5434
5435 while (count--)
5436 *relptr++ = tblptr++;
5437
5438 *relptr = (arelent *) NULL;
5439 return section->reloc_count;
5440}
23186865
JM
5441
5442/* Install a new set of internal relocs. */
5443
5444#define alpha_vms_set_reloc _bfd_generic_set_reloc
5445
95e34ef7
TG
5446\f
5447/* This is just copied from ecoff-alpha, needs to be fixed probably. */
5448
5449/* How to process the various reloc types. */
5450
5451static bfd_reloc_status_type
5452reloc_nil (bfd * abfd ATTRIBUTE_UNUSED,
5453 arelent *reloc ATTRIBUTE_UNUSED,
5454 asymbol *sym ATTRIBUTE_UNUSED,
5455 void * data ATTRIBUTE_UNUSED,
5456 asection *sec ATTRIBUTE_UNUSED,
5457 bfd *output_bfd ATTRIBUTE_UNUSED,
5458 char **error_message ATTRIBUTE_UNUSED)
5459{
5460#if VMS_DEBUG
5461 vms_debug (1, "reloc_nil (abfd %p, output_bfd %p)\n", abfd, output_bfd);
5462 vms_debug (2, "In section %s, symbol %s\n",
5463 sec->name, sym->name);
5464 vms_debug (2, "reloc sym %s, addr %08lx, addend %08lx, reloc is a %s\n",
5465 reloc->sym_ptr_ptr[0]->name,
5466 (unsigned long)reloc->address,
5467 (unsigned long)reloc->addend, reloc->howto->name);
5468 vms_debug (2, "data at %p\n", data);
5469 /* _bfd_hexdump (2, data, bfd_get_reloc_size (reloc->howto), 0); */
5470#endif
5471
5472 return bfd_reloc_ok;
5473}
5474
5475/* In case we're on a 32-bit machine, construct a 64-bit "-1" value
5476 from smaller values. Start with zero, widen, *then* decrement. */
5477#define MINUS_ONE (((bfd_vma)0) - 1)
5478
5479static reloc_howto_type alpha_howto_table[] =
5480{
5481 HOWTO (ALPHA_R_IGNORE, /* Type. */
5482 0, /* Rightshift. */
5483 0, /* Size (0 = byte, 1 = short, 2 = long). */
5484 8, /* Bitsize. */
5485 TRUE, /* PC relative. */
5486 0, /* Bitpos. */
5487 complain_overflow_dont,/* Complain_on_overflow. */
5488 reloc_nil, /* Special_function. */
5489 "IGNORE", /* Name. */
5490 TRUE, /* Partial_inplace. */
5491 0, /* Source mask */
5492 0, /* Dest mask. */
5493 TRUE), /* PC rel offset. */
5494
5495 /* A 64 bit reference to a symbol. */
5496 HOWTO (ALPHA_R_REFQUAD, /* Type. */
5497 0, /* Rightshift. */
5498 4, /* Size (0 = byte, 1 = short, 2 = long). */
5499 64, /* Bitsize. */
5500 FALSE, /* PC relative. */
5501 0, /* Bitpos. */
5502 complain_overflow_bitfield, /* Complain_on_overflow. */
5503 reloc_nil, /* Special_function. */
5504 "REFQUAD", /* Name. */
5505 TRUE, /* Partial_inplace. */
5506 MINUS_ONE, /* Source mask. */
5507 MINUS_ONE, /* Dest mask. */
5508 FALSE), /* PC rel offset. */
5509
5510 /* A 21 bit branch. The native assembler generates these for
5511 branches within the text segment, and also fills in the PC
5512 relative offset in the instruction. */
5513 HOWTO (ALPHA_R_BRADDR, /* Type. */
5514 2, /* Rightshift. */
5515 2, /* Size (0 = byte, 1 = short, 2 = long). */
5516 21, /* Bitsize. */
5517 TRUE, /* PC relative. */
5518 0, /* Bitpos. */
5519 complain_overflow_signed, /* Complain_on_overflow. */
5520 reloc_nil, /* Special_function. */
5521 "BRADDR", /* Name. */
5522 TRUE, /* Partial_inplace. */
5523 0x1fffff, /* Source mask. */
5524 0x1fffff, /* Dest mask. */
5525 FALSE), /* PC rel offset. */
5526
5527 /* A hint for a jump to a register. */
5528 HOWTO (ALPHA_R_HINT, /* Type. */
5529 2, /* Rightshift. */
5530 1, /* Size (0 = byte, 1 = short, 2 = long). */
5531 14, /* Bitsize. */
5532 TRUE, /* PC relative. */
5533 0, /* Bitpos. */
5534 complain_overflow_dont,/* Complain_on_overflow. */
5535 reloc_nil, /* Special_function. */
5536 "HINT", /* Name. */
5537 TRUE, /* Partial_inplace. */
5538 0x3fff, /* Source mask. */
5539 0x3fff, /* Dest mask. */
5540 FALSE), /* PC rel offset. */
5541
5542 /* 16 bit PC relative offset. */
5543 HOWTO (ALPHA_R_SREL16, /* Type. */
5544 0, /* Rightshift. */
5545 1, /* Size (0 = byte, 1 = short, 2 = long). */
5546 16, /* Bitsize. */
5547 TRUE, /* PC relative. */
5548 0, /* Bitpos. */
5549 complain_overflow_signed, /* Complain_on_overflow. */
5550 reloc_nil, /* Special_function. */
5551 "SREL16", /* Name. */
5552 TRUE, /* Partial_inplace. */
5553 0xffff, /* Source mask. */
5554 0xffff, /* Dest mask. */
5555 FALSE), /* PC rel offset. */
5556
5557 /* 32 bit PC relative offset. */
5558 HOWTO (ALPHA_R_SREL32, /* Type. */
5559 0, /* Rightshift. */
5560 2, /* Size (0 = byte, 1 = short, 2 = long). */
5561 32, /* Bitsize. */
5562 TRUE, /* PC relative. */
5563 0, /* Bitpos. */
5564 complain_overflow_signed, /* Complain_on_overflow. */
5565 reloc_nil, /* Special_function. */
5566 "SREL32", /* Name. */
5567 TRUE, /* Partial_inplace. */
5568 0xffffffff, /* Source mask. */
5569 0xffffffff, /* Dest mask. */
5570 FALSE), /* PC rel offset. */
5571
5572 /* A 64 bit PC relative offset. */
5573 HOWTO (ALPHA_R_SREL64, /* Type. */
5574 0, /* Rightshift. */
5575 4, /* Size (0 = byte, 1 = short, 2 = long). */
5576 64, /* Bitsize. */
5577 TRUE, /* PC relative. */
5578 0, /* Bitpos. */
5579 complain_overflow_signed, /* Complain_on_overflow. */
5580 reloc_nil, /* Special_function. */
5581 "SREL64", /* Name. */
5582 TRUE, /* Partial_inplace. */
5583 MINUS_ONE, /* Source mask. */
5584 MINUS_ONE, /* Dest mask. */
5585 FALSE), /* PC rel offset. */
5586
5587 /* Push a value on the reloc evaluation stack. */
5588 HOWTO (ALPHA_R_OP_PUSH, /* Type. */
5589 0, /* Rightshift. */
5590 0, /* Size (0 = byte, 1 = short, 2 = long). */
5591 0, /* Bitsize. */
5592 FALSE, /* PC relative. */
5593 0, /* Bitpos. */
5594 complain_overflow_dont,/* Complain_on_overflow. */
5595 reloc_nil, /* Special_function. */
5596 "OP_PUSH", /* Name. */
5597 FALSE, /* Partial_inplace. */
5598 0, /* Source mask. */
5599 0, /* Dest mask. */
5600 FALSE), /* PC rel offset. */
5601
5602 /* Store the value from the stack at the given address. Store it in
5603 a bitfield of size r_size starting at bit position r_offset. */
5604 HOWTO (ALPHA_R_OP_STORE, /* Type. */
5605 0, /* Rightshift. */
5606 4, /* Size (0 = byte, 1 = short, 2 = long). */
5607 64, /* Bitsize. */
5608 FALSE, /* PC relative. */
5609 0, /* Bitpos. */
5610 complain_overflow_dont,/* Complain_on_overflow. */
5611 reloc_nil, /* Special_function. */
5612 "OP_STORE", /* Name. */
5613 FALSE, /* Partial_inplace. */
5614 0, /* Source mask. */
5615 MINUS_ONE, /* Dest mask. */
5616 FALSE), /* PC rel offset. */
5617
5618 /* Subtract the reloc address from the value on the top of the
5619 relocation stack. */
5620 HOWTO (ALPHA_R_OP_PSUB, /* Type. */
5621 0, /* Rightshift. */
5622 0, /* Size (0 = byte, 1 = short, 2 = long). */
5623 0, /* Bitsize. */
5624 FALSE, /* PC relative. */
5625 0, /* Bitpos. */
5626 complain_overflow_dont,/* Complain_on_overflow. */
5627 reloc_nil, /* Special_function. */
5628 "OP_PSUB", /* Name. */
5629 FALSE, /* Partial_inplace. */
5630 0, /* Source mask. */
5631 0, /* Dest mask. */
5632 FALSE), /* PC rel offset. */
5633
5634 /* Shift the value on the top of the relocation stack right by the
5635 given value. */
5636 HOWTO (ALPHA_R_OP_PRSHIFT, /* Type. */
5637 0, /* Rightshift. */
5638 0, /* Size (0 = byte, 1 = short, 2 = long). */
5639 0, /* Bitsize. */
5640 FALSE, /* PC relative. */
5641 0, /* Bitpos. */
5642 complain_overflow_dont,/* Complain_on_overflow. */
5643 reloc_nil, /* Special_function. */
5644 "OP_PRSHIFT", /* Name. */
5645 FALSE, /* Partial_inplace. */
5646 0, /* Source mask. */
5647 0, /* Dest mask. */
5648 FALSE), /* PC rel offset. */
5649
5650 /* Hack. Linkage is done by linker. */
5651 HOWTO (ALPHA_R_LINKAGE, /* Type. */
5652 0, /* Rightshift. */
706704c8
AM
5653 0, /* Size (0 = byte, 1 = short, 2 = long). */
5654 0, /* Bitsize. */
95e34ef7
TG
5655 FALSE, /* PC relative. */
5656 0, /* Bitpos. */
5657 complain_overflow_dont,/* Complain_on_overflow. */
5658 reloc_nil, /* Special_function. */
5659 "LINKAGE", /* Name. */
5660 FALSE, /* Partial_inplace. */
5661 0, /* Source mask. */
5662 0, /* Dest mask. */
5663 FALSE), /* PC rel offset. */
5664
5665 /* A 32 bit reference to a symbol. */
5666 HOWTO (ALPHA_R_REFLONG, /* Type. */
5667 0, /* Rightshift. */
5668 2, /* Size (0 = byte, 1 = short, 2 = long). */
5669 32, /* Bitsize. */
5670 FALSE, /* PC relative. */
5671 0, /* Bitpos. */
5672 complain_overflow_bitfield, /* Complain_on_overflow. */
5673 reloc_nil, /* Special_function. */
5674 "REFLONG", /* Name. */
5675 TRUE, /* Partial_inplace. */
5676 0xffffffff, /* Source mask. */
5677 0xffffffff, /* Dest mask. */
5678 FALSE), /* PC rel offset. */
5679
5680 /* A 64 bit reference to a procedure, written as 32 bit value. */
5681 HOWTO (ALPHA_R_CODEADDR, /* Type. */
5682 0, /* Rightshift. */
5683 4, /* Size (0 = byte, 1 = short, 2 = long). */
5684 64, /* Bitsize. */
5685 FALSE, /* PC relative. */
5686 0, /* Bitpos. */
5687 complain_overflow_signed,/* Complain_on_overflow. */
5688 reloc_nil, /* Special_function. */
5689 "CODEADDR", /* Name. */
5690 FALSE, /* Partial_inplace. */
5691 0xffffffff, /* Source mask. */
5692 0xffffffff, /* Dest mask. */
5693 FALSE), /* PC rel offset. */
5694
5695 HOWTO (ALPHA_R_NOP, /* Type. */
5696 0, /* Rightshift. */
5697 3, /* Size (0 = byte, 1 = short, 2 = long). */
5698 0, /* Bitsize. */
5699 /* The following value must match that of ALPHA_R_BSR/ALPHA_R_BOH
5700 because the calculations for the 3 relocations are the same.
5701 See B.4.5.2 of the OpenVMS Linker Utility Manual. */
5702 TRUE, /* PC relative. */
5703 0, /* Bitpos. */
5704 complain_overflow_dont,/* Complain_on_overflow. */
5705 reloc_nil, /* Special_function. */
5706 "NOP", /* Name. */
5707 FALSE, /* Partial_inplace. */
5708 0xffffffff, /* Source mask. */
5709 0xffffffff, /* Dest mask. */
5710 FALSE), /* PC rel offset. */
5711
5712 HOWTO (ALPHA_R_BSR, /* Type. */
5713 0, /* Rightshift. */
5714 3, /* Size (0 = byte, 1 = short, 2 = long). */
5715 0, /* Bitsize. */
5716 TRUE, /* PC relative. */
5717 0, /* Bitpos. */
5718 complain_overflow_dont,/* Complain_on_overflow. */
5719 reloc_nil, /* Special_function. */
5720 "BSR", /* Name. */
5721 FALSE, /* Partial_inplace. */
5722 0xffffffff, /* Source mask. */
5723 0xffffffff, /* Dest mask. */
5724 FALSE), /* PC rel offset. */
5725
5726 HOWTO (ALPHA_R_LDA, /* Type. */
5727 0, /* Rightshift. */
5728 3, /* Size (0 = byte, 1 = short, 2 = long). */
5729 0, /* Bitsize. */
5730 FALSE, /* PC relative. */
5731 0, /* Bitpos. */
5732 complain_overflow_dont,/* Complain_on_overflow. */
5733 reloc_nil, /* Special_function. */
5734 "LDA", /* Name. */
5735 FALSE, /* Partial_inplace. */
5736 0xffffffff, /* Source mask. */
5737 0xffffffff, /* Dest mask. */
5738 FALSE), /* PC rel offset. */
5739
5740 HOWTO (ALPHA_R_BOH, /* Type. */
5741 0, /* Rightshift. */
5742 3, /* Size (0 = byte, 1 = short, 2 = long, 3 = nil). */
5743 0, /* Bitsize. */
5744 TRUE, /* PC relative. */
5745 0, /* Bitpos. */
5746 complain_overflow_dont,/* Complain_on_overflow. */
5747 reloc_nil, /* Special_function. */
5748 "BOH", /* Name. */
5749 FALSE, /* Partial_inplace. */
5750 0xffffffff, /* Source mask. */
5751 0xffffffff, /* Dest mask. */
5752 FALSE), /* PC rel offset. */
5753};
5754
5755/* Return a pointer to a howto structure which, when invoked, will perform
5756 the relocation code on data from the architecture noted. */
5757
487096bf 5758static reloc_howto_type *
95e34ef7 5759alpha_vms_bfd_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
07d6d2b8 5760 bfd_reloc_code_real_type code)
95e34ef7
TG
5761{
5762 int alpha_type;
5763
5764 vms_debug2 ((1, "vms_bfd_reloc_type_lookup (%p, %d)\t", abfd, code));
5765
5766 switch (code)
5767 {
5768 case BFD_RELOC_16: alpha_type = ALPHA_R_SREL16; break;
5769 case BFD_RELOC_32: alpha_type = ALPHA_R_REFLONG; break;
5770 case BFD_RELOC_64: alpha_type = ALPHA_R_REFQUAD; break;
5771 case BFD_RELOC_CTOR: alpha_type = ALPHA_R_REFQUAD; break;
5772 case BFD_RELOC_23_PCREL_S2: alpha_type = ALPHA_R_BRADDR; break;
5773 case BFD_RELOC_ALPHA_HINT: alpha_type = ALPHA_R_HINT; break;
5774 case BFD_RELOC_16_PCREL: alpha_type = ALPHA_R_SREL16; break;
5775 case BFD_RELOC_32_PCREL: alpha_type = ALPHA_R_SREL32; break;
5776 case BFD_RELOC_64_PCREL: alpha_type = ALPHA_R_SREL64; break;
5777 case BFD_RELOC_ALPHA_LINKAGE: alpha_type = ALPHA_R_LINKAGE; break;
5778 case BFD_RELOC_ALPHA_CODEADDR: alpha_type = ALPHA_R_CODEADDR; break;
5779 case BFD_RELOC_ALPHA_NOP: alpha_type = ALPHA_R_NOP; break;
5780 case BFD_RELOC_ALPHA_BSR: alpha_type = ALPHA_R_BSR; break;
5781 case BFD_RELOC_ALPHA_LDA: alpha_type = ALPHA_R_LDA; break;
5782 case BFD_RELOC_ALPHA_BOH: alpha_type = ALPHA_R_BOH; break;
5783 default:
695344c0 5784 _bfd_error_handler (_("reloc (%d) is *UNKNOWN*"), code);
95e34ef7
TG
5785 return NULL;
5786 }
5787 vms_debug2 ((2, "reloc is %s\n", alpha_howto_table[alpha_type].name));
5788 return & alpha_howto_table[alpha_type];
5789}
5790
5791static reloc_howto_type *
5792alpha_vms_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
07d6d2b8 5793 const char *r_name)
95e34ef7
TG
5794{
5795 unsigned int i;
5796
5797 for (i = 0;
5798 i < sizeof (alpha_howto_table) / sizeof (alpha_howto_table[0]);
5799 i++)
5800 if (alpha_howto_table[i].name != NULL
5801 && strcasecmp (alpha_howto_table[i].name, r_name) == 0)
5802 return &alpha_howto_table[i];
5803
5804 return NULL;
5805}
5806\f
5807static long
5808alpha_vms_get_synthetic_symtab (bfd *abfd,
07d6d2b8
AM
5809 long symcount ATTRIBUTE_UNUSED,
5810 asymbol **usyms ATTRIBUTE_UNUSED,
5811 long dynsymcount ATTRIBUTE_UNUSED,
5812 asymbol **dynsyms ATTRIBUTE_UNUSED,
5813 asymbol **ret)
95e34ef7
TG
5814{
5815 asymbol *syms;
5816 unsigned int i;
5817 unsigned int n = 0;
5818
5819 syms = (asymbol *) bfd_malloc (PRIV (norm_sym_count) * sizeof (asymbol));
5820 *ret = syms;
5821 if (syms == NULL)
5822 return -1;
5823
5824 for (i = 0; i < PRIV (gsd_sym_count); i++)
5825 {
5826 struct vms_symbol_entry *e = PRIV (syms)[i];
5827 asymbol *sym;
5828 flagword flags;
5829 symvalue value;
5830 asection *sec;
5831 const char *name;
5832 char *sname;
5833 int l;
5834
5835 name = e->name;
5836 value = 0;
5837 flags = BSF_LOCAL | BSF_SYNTHETIC;
5838 sec = NULL;
5839
5840 switch (e->typ)
07d6d2b8
AM
5841 {
5842 case EGSD__C_SYM:
5843 case EGSD__C_SYMG:
5844 if ((e->flags & EGSY__V_DEF) && (e->flags & EGSY__V_NORM))
5845 {
5846 value = e->code_value;
5847 sec = e->code_section;
5848 }
5849 else
5850 continue;
5851 break;
5852
5853 default:
5854 continue;
5855 }
95e34ef7
TG
5856
5857 l = strlen (name);
5858 sname = bfd_alloc (abfd, l + 5);
5859 if (sname == NULL)
07d6d2b8 5860 return FALSE;
95e34ef7
TG
5861 memcpy (sname, name, l);
5862 memcpy (sname + l, "..en", 5);
5863
5864 sym = &syms[n++];
5865 sym->name = sname;
5866 sym->section = sec;
5867 sym->flags = flags;
5868 sym->value = value;
5869 sym->udata.p = NULL;
5870 }
5871
5872 return n;
5873}
5874\f
5875/* Private dump. */
5876
5877static const char *
5878vms_time_to_str (unsigned char *buf)
5879{
5880 time_t t = vms_rawtime_to_time_t (buf);
5881 char *res = ctime (&t);
5882
5883 if (!res)
5884 res = "*invalid time*";
5885 else
5886 res[24] = 0;
5887 return res;
5888}
5889
5890static void
5891evax_bfd_print_emh (FILE *file, unsigned char *rec, unsigned int rec_len)
5892{
5893 struct vms_emh_common *emh = (struct vms_emh_common *)rec;
5894 unsigned int subtype;
8bdf0be1 5895 int extra;
95e34ef7 5896
8bdf0be1 5897 subtype = (unsigned) bfd_getl16 (emh->subtyp);
95e34ef7 5898
695344c0 5899 /* xgettext:c-format */
95e34ef7
TG
5900 fprintf (file, _(" EMH %u (len=%u): "), subtype, rec_len);
5901
bc21b167
NC
5902 /* PR 21618: Check for invalid lengths. */
5903 if (rec_len < sizeof (* emh))
5904 {
5905 fprintf (file, _(" Error: The length is less than the length of an EMH record\n"));
5906 return;
5907 }
8bdf0be1
NC
5908 extra = rec_len - sizeof (struct vms_emh_common);
5909
95e34ef7
TG
5910 switch (subtype)
5911 {
5912 case EMH__C_MHD:
5913 {
07d6d2b8
AM
5914 struct vms_emh_mhd *mhd = (struct vms_emh_mhd *) rec;
5915 const char * name;
8bdf0be1
NC
5916 const char * nextname;
5917 const char * maxname;
95e34ef7 5918
8bdf0be1
NC
5919 /* PR 21840: Check for invalid lengths. */
5920 if (rec_len < sizeof (* mhd))
5921 {
5922 fprintf (file, _(" Error: The record length is less than the size of an EMH_MHD record\n"));
5923 return;
5924 }
07d6d2b8
AM
5925 fprintf (file, _("Module header\n"));
5926 fprintf (file, _(" structure level: %u\n"), mhd->strlvl);
5927 fprintf (file, _(" max record size: %u\n"),
5928 (unsigned) bfd_getl32 (mhd->recsiz));
5929 name = (char *)(mhd + 1);
8bdf0be1
NC
5930 maxname = (char *) rec + rec_len;
5931 if (name > maxname - 2)
5932 {
5933 fprintf (file, _(" Error: The module name is missing\n"));
5934 return;
5935 }
5936 nextname = name + name[0] + 1;
5937 if (nextname >= maxname)
5938 {
5939 fprintf (file, _(" Error: The module name is too long\n"));
5940 return;
5941 }
07d6d2b8
AM
5942 fprintf (file, _(" module name : %.*s\n"), name[0], name + 1);
5943 name = nextname;
8bdf0be1
NC
5944 if (name > maxname - 2)
5945 {
5946 fprintf (file, _(" Error: The module version is missing\n"));
5947 return;
5948 }
5949 nextname = name + name[0] + 1;
5950 if (nextname >= maxname)
5951 {
5952 fprintf (file, _(" Error: The module version is too long\n"));
5953 return;
5954 }
07d6d2b8
AM
5955 fprintf (file, _(" module version : %.*s\n"), name[0], name + 1);
5956 name = nextname;
8bdf0be1
NC
5957 if ((maxname - name) < 17 && maxname[-1] != 0)
5958 fprintf (file, _(" Error: The compile date is truncated\n"));
5959 else
5960 fprintf (file, _(" compile date : %.17s\n"), name);
95e34ef7
TG
5961 }
5962 break;
8bdf0be1 5963
95e34ef7 5964 case EMH__C_LNM:
8bdf0be1
NC
5965 fprintf (file, _("Language Processor Name\n"));
5966 fprintf (file, _(" language name: %.*s\n"), extra, (char *)(emh + 1));
95e34ef7 5967 break;
8bdf0be1 5968
95e34ef7 5969 case EMH__C_SRC:
8bdf0be1
NC
5970 fprintf (file, _("Source Files Header\n"));
5971 fprintf (file, _(" file: %.*s\n"), extra, (char *)(emh + 1));
95e34ef7 5972 break;
8bdf0be1 5973
95e34ef7 5974 case EMH__C_TTL:
8bdf0be1
NC
5975 fprintf (file, _("Title Text Header\n"));
5976 fprintf (file, _(" title: %.*s\n"), extra, (char *)(emh + 1));
95e34ef7 5977 break;
8bdf0be1 5978
95e34ef7 5979 case EMH__C_CPR:
8bdf0be1
NC
5980 fprintf (file, _("Copyright Header\n"));
5981 fprintf (file, _(" copyright: %.*s\n"), extra, (char *)(emh + 1));
95e34ef7 5982 break;
8bdf0be1 5983
95e34ef7
TG
5984 default:
5985 fprintf (file, _("unhandled emh subtype %u\n"), subtype);
5986 break;
5987 }
5988}
5989
5990static void
5991evax_bfd_print_eeom (FILE *file, unsigned char *rec, unsigned int rec_len)
5992{
5993 struct vms_eeom *eeom = (struct vms_eeom *)rec;
5994
5995 fprintf (file, _(" EEOM (len=%u):\n"), rec_len);
bc21b167
NC
5996
5997 /* PR 21618: Check for invalid lengths. */
5998 if (rec_len < sizeof (* eeom))
5999 {
6000 fprintf (file, _(" Error: The length is less than the length of an EEOM record\n"));
6001 return;
6002 }
07d6d2b8 6003
95e34ef7 6004 fprintf (file, _(" number of cond linkage pairs: %u\n"),
07d6d2b8 6005 (unsigned)bfd_getl32 (eeom->total_lps));
95e34ef7 6006 fprintf (file, _(" completion code: %u\n"),
07d6d2b8 6007 (unsigned)bfd_getl16 (eeom->comcod));
95e34ef7
TG
6008 if (rec_len > 10)
6009 {
6010 fprintf (file, _(" transfer addr flags: 0x%02x\n"), eeom->tfrflg);
6011 fprintf (file, _(" transfer addr psect: %u\n"),
07d6d2b8 6012 (unsigned)bfd_getl32 (eeom->psindx));
95e34ef7 6013 fprintf (file, _(" transfer address : 0x%08x\n"),
07d6d2b8 6014 (unsigned)bfd_getl32 (eeom->tfradr));
95e34ef7
TG
6015 }
6016}
6017
6018static void
6019exav_bfd_print_egsy_flags (unsigned int flags, FILE *file)
6020{
6021 if (flags & EGSY__V_WEAK)
6022 fputs (_(" WEAK"), file);
6023 if (flags & EGSY__V_DEF)
6024 fputs (_(" DEF"), file);
6025 if (flags & EGSY__V_UNI)
6026 fputs (_(" UNI"), file);
6027 if (flags & EGSY__V_REL)
6028 fputs (_(" REL"), file);
6029 if (flags & EGSY__V_COMM)
6030 fputs (_(" COMM"), file);
6031 if (flags & EGSY__V_VECEP)
6032 fputs (_(" VECEP"), file);
6033 if (flags & EGSY__V_NORM)
6034 fputs (_(" NORM"), file);
6035 if (flags & EGSY__V_QUAD_VAL)
6036 fputs (_(" QVAL"), file);
6037}
6038
9a1b4480
TG
6039static void
6040evax_bfd_print_egsd_flags (FILE *file, unsigned int flags)
6041{
6042 if (flags & EGPS__V_PIC)
6043 fputs (_(" PIC"), file);
6044 if (flags & EGPS__V_LIB)
6045 fputs (_(" LIB"), file);
6046 if (flags & EGPS__V_OVR)
6047 fputs (_(" OVR"), file);
6048 if (flags & EGPS__V_REL)
6049 fputs (_(" REL"), file);
6050 if (flags & EGPS__V_GBL)
6051 fputs (_(" GBL"), file);
6052 if (flags & EGPS__V_SHR)
6053 fputs (_(" SHR"), file);
6054 if (flags & EGPS__V_EXE)
6055 fputs (_(" EXE"), file);
6056 if (flags & EGPS__V_RD)
6057 fputs (_(" RD"), file);
6058 if (flags & EGPS__V_WRT)
6059 fputs (_(" WRT"), file);
6060 if (flags & EGPS__V_VEC)
6061 fputs (_(" VEC"), file);
6062 if (flags & EGPS__V_NOMOD)
6063 fputs (_(" NOMOD"), file);
6064 if (flags & EGPS__V_COM)
6065 fputs (_(" COM"), file);
6066 if (flags & EGPS__V_ALLOC_64BIT)
6067 fputs (_(" 64B"), file);
6068}
6069
95e34ef7
TG
6070static void
6071evax_bfd_print_egsd (FILE *file, unsigned char *rec, unsigned int rec_len)
6072{
6073 unsigned int off = sizeof (struct vms_egsd);
6074 unsigned int n;
6075
6076 fprintf (file, _(" EGSD (len=%u):\n"), rec_len);
6077
6078 n = 0;
6079 for (off = sizeof (struct vms_egsd); off < rec_len; )
6080 {
6081 struct vms_egsd_entry *e = (struct vms_egsd_entry *)(rec + off);
6082 unsigned int type;
6083 unsigned int len;
6084
6085 type = (unsigned)bfd_getl16 (e->gsdtyp);
6086 len = (unsigned)bfd_getl16 (e->gsdsiz);
6087
695344c0 6088 /* xgettext:c-format */
95e34ef7 6089 fprintf (file, _(" EGSD entry %2u (type: %u, len: %u): "),
07d6d2b8 6090 n, type, len);
95e34ef7
TG
6091 n++;
6092
bc21b167
NC
6093 if (off + len > rec_len || off + len < off)
6094 {
6095 fprintf (file, _(" Error: length larger than remaining space in record\n"));
6096 return;
6097 }
6098
95e34ef7 6099 switch (type)
07d6d2b8
AM
6100 {
6101 case EGSD__C_PSC:
6102 {
6103 struct vms_egps *egps = (struct vms_egps *)e;
6104 unsigned int flags = bfd_getl16 (egps->flags);
6105 unsigned int l;
6106
6107 fprintf (file, _("PSC - Program section definition\n"));
6108 fprintf (file, _(" alignment : 2**%u\n"), egps->align);
6109 fprintf (file, _(" flags : 0x%04x"), flags);
6110 evax_bfd_print_egsd_flags (file, flags);
6111 fputc ('\n', file);
6112 l = bfd_getl32 (egps->alloc);
6113 fprintf (file, _(" alloc (len): %u (0x%08x)\n"), l, l);
6114 fprintf (file, _(" name : %.*s\n"),
6115 egps->namlng, egps->name);
6116 }
6117 break;
6118 case EGSD__C_SPSC:
6119 {
6120 struct vms_esgps *esgps = (struct vms_esgps *)e;
6121 unsigned int flags = bfd_getl16 (esgps->flags);
6122 unsigned int l;
6123
6124 fprintf (file, _("SPSC - Shared Image Program section def\n"));
6125 fprintf (file, _(" alignment : 2**%u\n"), esgps->align);
6126 fprintf (file, _(" flags : 0x%04x"), flags);
6127 evax_bfd_print_egsd_flags (file, flags);
6128 fputc ('\n', file);
6129 l = bfd_getl32 (esgps->alloc);
6130 fprintf (file, _(" alloc (len) : %u (0x%08x)\n"), l, l);
6131 fprintf (file, _(" image offset : 0x%08x\n"),
6132 (unsigned int)bfd_getl32 (esgps->base));
6133 fprintf (file, _(" symvec offset : 0x%08x\n"),
6134 (unsigned int)bfd_getl32 (esgps->value));
6135 fprintf (file, _(" name : %.*s\n"),
6136 esgps->namlng, esgps->name);
6137 }
6138 break;
6139 case EGSD__C_SYM:
6140 {
6141 struct vms_egsy *egsy = (struct vms_egsy *)e;
6142 unsigned int flags = bfd_getl16 (egsy->flags);
6143
6144 if (flags & EGSY__V_DEF)
6145 {
6146 struct vms_esdf *esdf = (struct vms_esdf *)e;
6147
6148 fprintf (file, _("SYM - Global symbol definition\n"));
6149 fprintf (file, _(" flags: 0x%04x"), flags);
6150 exav_bfd_print_egsy_flags (flags, file);
6151 fputc ('\n', file);
6152 fprintf (file, _(" psect offset: 0x%08x\n"),
6153 (unsigned)bfd_getl32 (esdf->value));
6154 if (flags & EGSY__V_NORM)
6155 {
6156 fprintf (file, _(" code address: 0x%08x\n"),
6157 (unsigned)bfd_getl32 (esdf->code_address));
6158 fprintf (file, _(" psect index for entry point : %u\n"),
6159 (unsigned)bfd_getl32 (esdf->ca_psindx));
6160 }
6161 fprintf (file, _(" psect index : %u\n"),
6162 (unsigned)bfd_getl32 (esdf->psindx));
6163 fprintf (file, _(" name : %.*s\n"),
6164 esdf->namlng, esdf->name);
6165 }
6166 else
6167 {
6168 struct vms_esrf *esrf = (struct vms_esrf *)e;
6169
6170 fprintf (file, _("SYM - Global symbol reference\n"));
6171 fprintf (file, _(" name : %.*s\n"),
6172 esrf->namlng, esrf->name);
6173 }
6174 }
6175 break;
6176 case EGSD__C_IDC:
6177 {
6178 struct vms_eidc *eidc = (struct vms_eidc *)e;
6179 unsigned int flags = bfd_getl32 (eidc->flags);
6180 unsigned char *p;
6181
6182 fprintf (file, _("IDC - Ident Consistency check\n"));
6183 fprintf (file, _(" flags : 0x%08x"), flags);
6184 if (flags & EIDC__V_BINIDENT)
6185 fputs (" BINDENT", file);
6186 fputc ('\n', file);
6187 fprintf (file, _(" id match : %x\n"),
6188 (flags >> EIDC__V_IDMATCH_SH) & EIDC__V_IDMATCH_MASK);
6189 fprintf (file, _(" error severity: %x\n"),
6190 (flags >> EIDC__V_ERRSEV_SH) & EIDC__V_ERRSEV_MASK);
6191 p = eidc->name;
6192 fprintf (file, _(" entity name : %.*s\n"), p[0], p + 1);
6193 p += 1 + p[0];
6194 fprintf (file, _(" object name : %.*s\n"), p[0], p + 1);
6195 p += 1 + p[0];
6196 if (flags & EIDC__V_BINIDENT)
6197 fprintf (file, _(" binary ident : 0x%08x\n"),
6198 (unsigned)bfd_getl32 (p + 1));
6199 else
6200 fprintf (file, _(" ascii ident : %.*s\n"), p[0], p + 1);
6201 }
6202 break;
6203 case EGSD__C_SYMG:
6204 {
6205 struct vms_egst *egst = (struct vms_egst *)e;
6206 unsigned int flags = bfd_getl16 (egst->header.flags);
6207
6208 fprintf (file, _("SYMG - Universal symbol definition\n"));
6209 fprintf (file, _(" flags: 0x%04x"), flags);
6210 exav_bfd_print_egsy_flags (flags, file);
6211 fputc ('\n', file);
6212 fprintf (file, _(" symbol vector offset: 0x%08x\n"),
6213 (unsigned)bfd_getl32 (egst->value));
6214 fprintf (file, _(" entry point: 0x%08x\n"),
6215 (unsigned)bfd_getl32 (egst->lp_1));
6216 fprintf (file, _(" proc descr : 0x%08x\n"),
6217 (unsigned)bfd_getl32 (egst->lp_2));
6218 fprintf (file, _(" psect index: %u\n"),
6219 (unsigned)bfd_getl32 (egst->psindx));
6220 fprintf (file, _(" name : %.*s\n"),
6221 egst->namlng, egst->name);
6222 }
6223 break;
6224 case EGSD__C_SYMV:
6225 {
6226 struct vms_esdfv *esdfv = (struct vms_esdfv *)e;
6227 unsigned int flags = bfd_getl16 (esdfv->flags);
6228
6229 fprintf (file, _("SYMV - Vectored symbol definition\n"));
6230 fprintf (file, _(" flags: 0x%04x"), flags);
6231 exav_bfd_print_egsy_flags (flags, file);
6232 fputc ('\n', file);
6233 fprintf (file, _(" vector : 0x%08x\n"),
6234 (unsigned)bfd_getl32 (esdfv->vector));
6235 fprintf (file, _(" psect offset: %u\n"),
6236 (unsigned)bfd_getl32 (esdfv->value));
6237 fprintf (file, _(" psect index : %u\n"),
6238 (unsigned)bfd_getl32 (esdfv->psindx));
6239 fprintf (file, _(" name : %.*s\n"),
6240 esdfv->namlng, esdfv->name);
6241 }
6242 break;
6243 case EGSD__C_SYMM:
6244 {
6245 struct vms_esdfm *esdfm = (struct vms_esdfm *)e;
6246 unsigned int flags = bfd_getl16 (esdfm->flags);
6247
6248 fprintf (file, _("SYMM - Global symbol definition with version\n"));
6249 fprintf (file, _(" flags: 0x%04x"), flags);
6250 exav_bfd_print_egsy_flags (flags, file);
6251 fputc ('\n', file);
6252 fprintf (file, _(" version mask: 0x%08x\n"),
6253 (unsigned)bfd_getl32 (esdfm->version_mask));
6254 fprintf (file, _(" psect offset: %u\n"),
6255 (unsigned)bfd_getl32 (esdfm->value));
6256 fprintf (file, _(" psect index : %u\n"),
6257 (unsigned)bfd_getl32 (esdfm->psindx));
6258 fprintf (file, _(" name : %.*s\n"),
6259 esdfm->namlng, esdfm->name);
6260 }
6261 break;
6262 default:
6263 fprintf (file, _("unhandled egsd entry type %u\n"), type);
6264 break;
6265 }
95e34ef7
TG
6266 off += len;
6267 }
6268}
6269
6270static void
6271evax_bfd_print_hex (FILE *file, const char *pfx,
07d6d2b8 6272 const unsigned char *buf, unsigned int len)
95e34ef7
TG
6273{
6274 unsigned int i;
6275 unsigned int n;
6276
6277 n = 0;
6278 for (i = 0; i < len; i++)
6279 {
6280 if (n == 0)
07d6d2b8 6281 fputs (pfx, file);
95e34ef7
TG
6282 fprintf (file, " %02x", buf[i]);
6283 n++;
6284 if (n == 16)
07d6d2b8
AM
6285 {
6286 n = 0;
6287 fputc ('\n', file);
6288 }
95e34ef7
TG
6289 }
6290 if (n != 0)
6291 fputc ('\n', file);
6292}
6293
6294static void
6295evax_bfd_print_etir_stc_ir (FILE *file, const unsigned char *buf, int is_ps)
6296{
695344c0 6297 /* xgettext:c-format */
95e34ef7 6298 fprintf (file, _(" linkage index: %u, replacement insn: 0x%08x\n"),
07d6d2b8
AM
6299 (unsigned)bfd_getl32 (buf),
6300 (unsigned)bfd_getl32 (buf + 16));
695344c0 6301 /* xgettext:c-format */
95e34ef7 6302 fprintf (file, _(" psect idx 1: %u, offset 1: 0x%08x %08x\n"),
07d6d2b8
AM
6303 (unsigned)bfd_getl32 (buf + 4),
6304 (unsigned)bfd_getl32 (buf + 12),
6305 (unsigned)bfd_getl32 (buf + 8));
695344c0 6306 /* xgettext:c-format */
95e34ef7 6307 fprintf (file, _(" psect idx 2: %u, offset 2: 0x%08x %08x\n"),
07d6d2b8
AM
6308 (unsigned)bfd_getl32 (buf + 20),
6309 (unsigned)bfd_getl32 (buf + 28),
6310 (unsigned)bfd_getl32 (buf + 24));
95e34ef7 6311 if (is_ps)
695344c0 6312 /* xgettext:c-format */
95e34ef7 6313 fprintf (file, _(" psect idx 3: %u, offset 3: 0x%08x %08x\n"),
07d6d2b8
AM
6314 (unsigned)bfd_getl32 (buf + 32),
6315 (unsigned)bfd_getl32 (buf + 40),
6316 (unsigned)bfd_getl32 (buf + 36));
95e34ef7
TG
6317 else
6318 fprintf (file, _(" global name: %.*s\n"), buf[32], buf + 33);
6319}
6320
6321static void
6322evax_bfd_print_etir (FILE *file, const char *name,
07d6d2b8 6323 unsigned char *rec, unsigned int rec_len)
95e34ef7
TG
6324{
6325 unsigned int off = sizeof (struct vms_egsd);
544008aa 6326 unsigned int sec_len = 0;
95e34ef7 6327
695344c0 6328 /* xgettext:c-format */
95e34ef7 6329 fprintf (file, _(" %s (len=%u+%u):\n"), name,
07d6d2b8
AM
6330 (unsigned)(rec_len - sizeof (struct vms_eobjrec)),
6331 (unsigned)sizeof (struct vms_eobjrec));
95e34ef7
TG
6332
6333 for (off = sizeof (struct vms_eobjrec); off < rec_len; )
6334 {
6335 struct vms_etir *etir = (struct vms_etir *)(rec + off);
6336 unsigned char *buf;
6337 unsigned int type;
6338 unsigned int size;
6339
6340 type = bfd_getl16 (etir->rectyp);
6341 size = bfd_getl16 (etir->size);
6342 buf = rec + off + sizeof (struct vms_etir);
6343
bc21b167
NC
6344 if (off + size > rec_len || off + size < off)
6345 {
6346 fprintf (file, _(" Error: length larger than remaining space in record\n"));
6347 return;
6348 }
6349
695344c0 6350 /* xgettext:c-format */
95e34ef7
TG
6351 fprintf (file, _(" (type: %3u, size: 4+%3u): "), type, size - 4);
6352 switch (type)
07d6d2b8
AM
6353 {
6354 case ETIR__C_STA_GBL:
6355 fprintf (file, _("STA_GBL (stack global) %.*s\n"),
6356 buf[0], buf + 1);
6357 break;
6358 case ETIR__C_STA_LW:
6359 fprintf (file, _("STA_LW (stack longword) 0x%08x\n"),
6360 (unsigned)bfd_getl32 (buf));
6361 break;
6362 case ETIR__C_STA_QW:
6363 fprintf (file, _("STA_QW (stack quadword) 0x%08x %08x\n"),
6364 (unsigned)bfd_getl32 (buf + 4),
6365 (unsigned)bfd_getl32 (buf + 0));
6366 break;
6367 case ETIR__C_STA_PQ:
6368 fprintf (file, _("STA_PQ (stack psect base + offset)\n"));
695344c0 6369 /* xgettext:c-format */
07d6d2b8
AM
6370 fprintf (file, _(" psect: %u, offset: 0x%08x %08x\n"),
6371 (unsigned)bfd_getl32 (buf + 0),
6372 (unsigned)bfd_getl32 (buf + 8),
6373 (unsigned)bfd_getl32 (buf + 4));
6374 break;
6375 case ETIR__C_STA_LI:
6376 fprintf (file, _("STA_LI (stack literal)\n"));
6377 break;
6378 case ETIR__C_STA_MOD:
6379 fprintf (file, _("STA_MOD (stack module)\n"));
6380 break;
6381 case ETIR__C_STA_CKARG:
6382 fprintf (file, _("STA_CKARG (compare procedure argument)\n"));
6383 break;
6384
6385 case ETIR__C_STO_B:
6386 fprintf (file, _("STO_B (store byte)\n"));
6387 break;
6388 case ETIR__C_STO_W:
6389 fprintf (file, _("STO_W (store word)\n"));
6390 break;
6391 case ETIR__C_STO_LW:
6392 fprintf (file, _("STO_LW (store longword)\n"));
6393 break;
6394 case ETIR__C_STO_QW:
6395 fprintf (file, _("STO_QW (store quadword)\n"));
6396 break;
6397 case ETIR__C_STO_IMMR:
6398 {
6399 unsigned int len = bfd_getl32 (buf);
6400 fprintf (file,
6401 _("STO_IMMR (store immediate repeat) %u bytes\n"),
6402 len);
6403 evax_bfd_print_hex (file, " ", buf + 4, len);
6404 sec_len += len;
6405 }
6406 break;
6407 case ETIR__C_STO_GBL:
6408 fprintf (file, _("STO_GBL (store global) %.*s\n"),
6409 buf[0], buf + 1);
6410 break;
6411 case ETIR__C_STO_CA:
6412 fprintf (file, _("STO_CA (store code address) %.*s\n"),
6413 buf[0], buf + 1);
6414 break;
6415 case ETIR__C_STO_RB:
6416 fprintf (file, _("STO_RB (store relative branch)\n"));
6417 break;
6418 case ETIR__C_STO_AB:
6419 fprintf (file, _("STO_AB (store absolute branch)\n"));
6420 break;
6421 case ETIR__C_STO_OFF:
6422 fprintf (file, _("STO_OFF (store offset to psect)\n"));
6423 break;
6424 case ETIR__C_STO_IMM:
6425 {
6426 unsigned int len = bfd_getl32 (buf);
6427 fprintf (file,
6428 _("STO_IMM (store immediate) %u bytes\n"),
6429 len);
6430 evax_bfd_print_hex (file, " ", buf + 4, len);
6431 sec_len += len;
6432 }
6433 break;
6434 case ETIR__C_STO_GBL_LW:
6435 fprintf (file, _("STO_GBL_LW (store global longword) %.*s\n"),
6436 buf[0], buf + 1);
6437 break;
6438 case ETIR__C_STO_LP_PSB:
6439 fprintf (file, _("STO_OFF (store LP with procedure signature)\n"));
6440 break;
6441 case ETIR__C_STO_HINT_GBL:
6442 fprintf (file, _("STO_BR_GBL (store branch global) *todo*\n"));
6443 break;
6444 case ETIR__C_STO_HINT_PS:
6445 fprintf (file, _("STO_BR_PS (store branch psect + offset) *todo*\n"));
6446 break;
6447
6448 case ETIR__C_OPR_NOP:
6449 fprintf (file, _("OPR_NOP (no-operation)\n"));
6450 break;
6451 case ETIR__C_OPR_ADD:
6452 fprintf (file, _("OPR_ADD (add)\n"));
6453 break;
6454 case ETIR__C_OPR_SUB:
6455 fprintf (file, _("OPR_SUB (subtract)\n"));
6456 break;
6457 case ETIR__C_OPR_MUL:
6458 fprintf (file, _("OPR_MUL (multiply)\n"));
6459 break;
6460 case ETIR__C_OPR_DIV:
6461 fprintf (file, _("OPR_DIV (divide)\n"));
6462 break;
6463 case ETIR__C_OPR_AND:
6464 fprintf (file, _("OPR_AND (logical and)\n"));
6465 break;
6466 case ETIR__C_OPR_IOR:
6467 fprintf (file, _("OPR_IOR (logical inclusive or)\n"));
6468 break;
6469 case ETIR__C_OPR_EOR:
6470 fprintf (file, _("OPR_EOR (logical exclusive or)\n"));
6471 break;
6472 case ETIR__C_OPR_NEG:
6473 fprintf (file, _("OPR_NEG (negate)\n"));
6474 break;
6475 case ETIR__C_OPR_COM:
6476 fprintf (file, _("OPR_COM (complement)\n"));
6477 break;
6478 case ETIR__C_OPR_INSV:
6479 fprintf (file, _("OPR_INSV (insert field)\n"));
6480 break;
6481 case ETIR__C_OPR_ASH:
6482 fprintf (file, _("OPR_ASH (arithmetic shift)\n"));
6483 break;
6484 case ETIR__C_OPR_USH:
6485 fprintf (file, _("OPR_USH (unsigned shift)\n"));
6486 break;
6487 case ETIR__C_OPR_ROT:
6488 fprintf (file, _("OPR_ROT (rotate)\n"));
6489 break;
6490 case ETIR__C_OPR_SEL:
6491 fprintf (file, _("OPR_SEL (select)\n"));
6492 break;
6493 case ETIR__C_OPR_REDEF:
6494 fprintf (file, _("OPR_REDEF (redefine symbol to curr location)\n"));
6495 break;
6496 case ETIR__C_OPR_DFLIT:
6497 fprintf (file, _("OPR_REDEF (define a literal)\n"));
6498 break;
6499
6500 case ETIR__C_STC_LP:
6501 fprintf (file, _("STC_LP (store cond linkage pair)\n"));
6502 break;
6503 case ETIR__C_STC_LP_PSB:
6504 fprintf (file,
6505 _("STC_LP_PSB (store cond linkage pair + signature)\n"));
695344c0 6506 /* xgettext:c-format */
07d6d2b8
AM
6507 fprintf (file, _(" linkage index: %u, procedure: %.*s\n"),
6508 (unsigned)bfd_getl32 (buf), buf[4], buf + 5);
6509 buf += 4 + 1 + buf[4];
6510 fprintf (file, _(" signature: %.*s\n"), buf[0], buf + 1);
6511 break;
6512 case ETIR__C_STC_GBL:
6513 fprintf (file, _("STC_GBL (store cond global)\n"));
695344c0 6514 /* xgettext:c-format */
07d6d2b8
AM
6515 fprintf (file, _(" linkage index: %u, global: %.*s\n"),
6516 (unsigned)bfd_getl32 (buf), buf[4], buf + 5);
6517 break;
6518 case ETIR__C_STC_GCA:
6519 fprintf (file, _("STC_GCA (store cond code address)\n"));
695344c0 6520 /* xgettext:c-format */
07d6d2b8
AM
6521 fprintf (file, _(" linkage index: %u, procedure name: %.*s\n"),
6522 (unsigned)bfd_getl32 (buf), buf[4], buf + 5);
6523 break;
6524 case ETIR__C_STC_PS:
6525 fprintf (file, _("STC_PS (store cond psect + offset)\n"));
6526 fprintf (file,
695344c0 6527 /* xgettext:c-format */
07d6d2b8
AM
6528 _(" linkage index: %u, psect: %u, offset: 0x%08x %08x\n"),
6529 (unsigned)bfd_getl32 (buf),
6530 (unsigned)bfd_getl32 (buf + 4),
6531 (unsigned)bfd_getl32 (buf + 12),
6532 (unsigned)bfd_getl32 (buf + 8));
6533 break;
6534 case ETIR__C_STC_NOP_GBL:
6535 fprintf (file, _("STC_NOP_GBL (store cond NOP at global addr)\n"));
6536 evax_bfd_print_etir_stc_ir (file, buf, 0);
6537 break;
6538 case ETIR__C_STC_NOP_PS:
6539 fprintf (file, _("STC_NOP_PS (store cond NOP at psect + offset)\n"));
6540 evax_bfd_print_etir_stc_ir (file, buf, 1);
6541 break;
6542 case ETIR__C_STC_BSR_GBL:
6543 fprintf (file, _("STC_BSR_GBL (store cond BSR at global addr)\n"));
6544 evax_bfd_print_etir_stc_ir (file, buf, 0);
6545 break;
6546 case ETIR__C_STC_BSR_PS:
6547 fprintf (file, _("STC_BSR_PS (store cond BSR at psect + offset)\n"));
6548 evax_bfd_print_etir_stc_ir (file, buf, 1);
6549 break;
6550 case ETIR__C_STC_LDA_GBL:
6551 fprintf (file, _("STC_LDA_GBL (store cond LDA at global addr)\n"));
6552 evax_bfd_print_etir_stc_ir (file, buf, 0);
6553 break;
6554 case ETIR__C_STC_LDA_PS:
6555 fprintf (file, _("STC_LDA_PS (store cond LDA at psect + offset)\n"));
6556 evax_bfd_print_etir_stc_ir (file, buf, 1);
6557 break;
6558 case ETIR__C_STC_BOH_GBL:
6559 fprintf (file, _("STC_BOH_GBL (store cond BOH at global addr)\n"));
6560 evax_bfd_print_etir_stc_ir (file, buf, 0);
6561 break;
6562 case ETIR__C_STC_BOH_PS:
6563 fprintf (file, _("STC_BOH_PS (store cond BOH at psect + offset)\n"));
6564 evax_bfd_print_etir_stc_ir (file, buf, 1);
6565 break;
6566 case ETIR__C_STC_NBH_GBL:
6567 fprintf (file,
6568 _("STC_NBH_GBL (store cond or hint at global addr)\n"));
6569 break;
6570 case ETIR__C_STC_NBH_PS:
6571 fprintf (file,
6572 _("STC_NBH_PS (store cond or hint at psect + offset)\n"));
6573 break;
6574
6575 case ETIR__C_CTL_SETRB:
6576 fprintf (file, _("CTL_SETRB (set relocation base)\n"));
6577 sec_len += 4;
6578 break;
6579 case ETIR__C_CTL_AUGRB:
6580 {
6581 unsigned int val = bfd_getl32 (buf);
6582 fprintf (file, _("CTL_AUGRB (augment relocation base) %u\n"), val);
6583 }
6584 break;
6585 case ETIR__C_CTL_DFLOC:
6586 fprintf (file, _("CTL_DFLOC (define location)\n"));
6587 break;
6588 case ETIR__C_CTL_STLOC:
6589 fprintf (file, _("CTL_STLOC (set location)\n"));
6590 break;
6591 case ETIR__C_CTL_STKDL:
6592 fprintf (file, _("CTL_STKDL (stack defined location)\n"));
6593 break;
6594 default:
6595 fprintf (file, _("*unhandled*\n"));
6596 break;
6597 }
95e34ef7
TG
6598 off += size;
6599 }
6600}
6601
6602static void
6603evax_bfd_print_eobj (struct bfd *abfd, FILE *file)
6604{
6605 bfd_boolean is_first = TRUE;
6606 bfd_boolean has_records = FALSE;
6607
6608 while (1)
6609 {
6610 unsigned int rec_len;
6611 unsigned int pad_len;
6612 unsigned char *rec;
6613 unsigned int hdr_size;
6614 unsigned int type;
6615
6616 if (is_first)
07d6d2b8
AM
6617 {
6618 unsigned char buf[6];
6619
6620 is_first = FALSE;
6621
6622 /* Read 6 bytes. */
6623 if (bfd_bread (buf, sizeof (buf), abfd) != sizeof (buf))
6624 {
6625 fprintf (file, _("cannot read GST record length\n"));
6626 return;
6627 }
6628 rec_len = bfd_getl16 (buf + 0);
6629 if (rec_len == bfd_getl16 (buf + 4)
6630 && bfd_getl16 (buf + 2) == EOBJ__C_EMH)
6631 {
6632 /* The format is raw: record-size, type, record-size. */
6633 has_records = TRUE;
6634 pad_len = (rec_len + 1) & ~1U;
6635 hdr_size = 4;
6636 }
6637 else if (rec_len == EOBJ__C_EMH)
6638 {
6639 has_records = FALSE;
6640 pad_len = bfd_getl16 (buf + 2);
6641 hdr_size = 6;
6642 }
6643 else
6644 {
6645 /* Ill-formed. */
6646 fprintf (file, _("cannot find EMH in first GST record\n"));
6647 return;
6648 }
6649 rec = bfd_malloc (pad_len);
6650 memcpy (rec, buf + sizeof (buf) - hdr_size, hdr_size);
6651 }
6652 else
6653 {
6654 unsigned int rec_len2 = 0;
6655 unsigned char hdr[4];
6656
6657 if (has_records)
6658 {
6659 unsigned char buf_len[2];
6660
6661 if (bfd_bread (buf_len, sizeof (buf_len), abfd)
6662 != sizeof (buf_len))
6663 {
6664 fprintf (file, _("cannot read GST record length\n"));
6665 return;
6666 }
6667 rec_len2 = (unsigned)bfd_getl16 (buf_len);
6668 }
6669
6670 if (bfd_bread (hdr, sizeof (hdr), abfd) != sizeof (hdr))
6671 {
6672 fprintf (file, _("cannot read GST record header\n"));
6673 return;
6674 }
6675 rec_len = (unsigned)bfd_getl16 (hdr + 2);
6676 if (has_records)
6677 pad_len = (rec_len + 1) & ~1U;
6678 else
6679 pad_len = rec_len;
6680 rec = bfd_malloc (pad_len);
6681 memcpy (rec, hdr, sizeof (hdr));
6682 hdr_size = sizeof (hdr);
6683 if (has_records && rec_len2 != rec_len)
6684 {
6685 fprintf (file, _(" corrupted GST\n"));
6686 break;
6687 }
6688 }
95e34ef7
TG
6689
6690 if (bfd_bread (rec + hdr_size, pad_len - hdr_size, abfd)
07d6d2b8
AM
6691 != pad_len - hdr_size)
6692 {
6693 fprintf (file, _("cannot read GST record\n"));
6694 return;
6695 }
95e34ef7
TG
6696
6697 type = (unsigned)bfd_getl16 (rec);
6698
6699 switch (type)
07d6d2b8
AM
6700 {
6701 case EOBJ__C_EMH:
6702 evax_bfd_print_emh (file, rec, rec_len);
6703 break;
6704 case EOBJ__C_EGSD:
6705 evax_bfd_print_egsd (file, rec, rec_len);
6706 break;
6707 case EOBJ__C_EEOM:
6708 evax_bfd_print_eeom (file, rec, rec_len);
6709 free (rec);
6710 return;
6711 break;
6712 case EOBJ__C_ETIR:
6713 evax_bfd_print_etir (file, "ETIR", rec, rec_len);
6714 break;
6715 case EOBJ__C_EDBG:
6716 evax_bfd_print_etir (file, "EDBG", rec, rec_len);
6717 break;
6718 case EOBJ__C_ETBT:
6719 evax_bfd_print_etir (file, "ETBT", rec, rec_len);
6720 break;
6721 default:
6722 fprintf (file, _(" unhandled EOBJ record type %u\n"), type);
6723 break;
6724 }
95e34ef7
TG
6725 free (rec);
6726 }
6727}
6728
6729static void
6730evax_bfd_print_relocation_records (FILE *file, const unsigned char *rel,
07d6d2b8 6731 unsigned int stride)
95e34ef7
TG
6732{
6733 while (1)
6734 {
6735 unsigned int base;
6736 unsigned int count;
6737 unsigned int j;
6738
6739 count = bfd_getl32 (rel + 0);
6740
6741 if (count == 0)
07d6d2b8 6742 break;
95e34ef7
TG
6743 base = bfd_getl32 (rel + 4);
6744
695344c0 6745 /* xgettext:c-format */
95e34ef7 6746 fprintf (file, _(" bitcount: %u, base addr: 0x%08x\n"),
07d6d2b8 6747 count, base);
95e34ef7
TG
6748
6749 rel += 8;
6750 for (j = 0; count > 0; j += 4, count -= 32)
07d6d2b8
AM
6751 {
6752 unsigned int k;
6753 unsigned int n = 0;
6754 unsigned int val;
95e34ef7 6755
07d6d2b8
AM
6756 val = bfd_getl32 (rel);
6757 rel += 4;
95e34ef7 6758
695344c0 6759 /* xgettext:c-format */
07d6d2b8
AM
6760 fprintf (file, _(" bitmap: 0x%08x (count: %u):\n"), val, count);
6761
6762 for (k = 0; k < 32; k++)
401e101e 6763 if (val & (1u << k))
07d6d2b8
AM
6764 {
6765 if (n == 0)
6766 fputs (" ", file);
6767 fprintf (file, _(" %08x"), base + (j * 8 + k) * stride);
6768 n++;
6769 if (n == 8)
6770 {
6771 fputs ("\n", file);
6772 n = 0;
6773 }
6774 }
6775 if (n)
6776 fputs ("\n", file);
6777 }
95e34ef7
TG
6778 }
6779}
6780
6781static void
6782evax_bfd_print_address_fixups (FILE *file, const unsigned char *rel)
6783{
6784 while (1)
6785 {
6786 unsigned int j;
6787 unsigned int count;
6788
6789 count = bfd_getl32 (rel + 0);
6790 if (count == 0)
07d6d2b8 6791 return;
695344c0 6792 /* xgettext:c-format */
95e34ef7 6793 fprintf (file, _(" image %u (%u entries)\n"),
07d6d2b8 6794 (unsigned)bfd_getl32 (rel + 4), count);
95e34ef7
TG
6795 rel += 8;
6796 for (j = 0; j < count; j++)
07d6d2b8 6797 {
695344c0 6798 /* xgettext:c-format */
07d6d2b8
AM
6799 fprintf (file, _(" offset: 0x%08x, val: 0x%08x\n"),
6800 (unsigned)bfd_getl32 (rel + 0),
6801 (unsigned)bfd_getl32 (rel + 4));
6802 rel += 8;
6803 }
95e34ef7
TG
6804 }
6805}
6806
6807static void
6808evax_bfd_print_reference_fixups (FILE *file, const unsigned char *rel)
6809{
6810 unsigned int count;
6811
6812 while (1)
6813 {
6814 unsigned int j;
6815 unsigned int n = 0;
6816
6817 count = bfd_getl32 (rel + 0);
6818 if (count == 0)
07d6d2b8 6819 break;
695344c0 6820 /* xgettext:c-format */
95e34ef7 6821 fprintf (file, _(" image %u (%u entries), offsets:\n"),
07d6d2b8 6822 (unsigned)bfd_getl32 (rel + 4), count);
95e34ef7
TG
6823 rel += 8;
6824 for (j = 0; j < count; j++)
07d6d2b8
AM
6825 {
6826 if (n == 0)
6827 fputs (" ", file);
6828 fprintf (file, _(" 0x%08x"), (unsigned)bfd_getl32 (rel));
6829 n++;
6830 if (n == 7)
6831 {
6832 fputs ("\n", file);
6833 n = 0;
6834 }
6835 rel += 4;
6836 }
95e34ef7 6837 if (n)
07d6d2b8 6838 fputs ("\n", file);
95e34ef7
TG
6839 }
6840}
6841
6842static void
6843evax_bfd_print_indent (int indent, FILE *file)
6844{
6845 for (; indent; indent--)
6846 fputc (' ', file);
6847}
6848
6849static const char *
6850evax_bfd_get_dsc_name (unsigned int v)
6851{
6852 switch (v)
6853 {
6854 case DSC__K_DTYPE_Z:
6855 return "Z (Unspecified)";
6856 case DSC__K_DTYPE_V:
6857 return "V (Bit)";
6858 case DSC__K_DTYPE_BU:
6859 return "BU (Byte logical)";
6860 case DSC__K_DTYPE_WU:
6861 return "WU (Word logical)";
6862 case DSC__K_DTYPE_LU:
6863 return "LU (Longword logical)";
6864 case DSC__K_DTYPE_QU:
6865 return "QU (Quadword logical)";
6866 case DSC__K_DTYPE_B:
6867 return "B (Byte integer)";
6868 case DSC__K_DTYPE_W:
6869 return "W (Word integer)";
6870 case DSC__K_DTYPE_L:
6871 return "L (Longword integer)";
6872 case DSC__K_DTYPE_Q:
6873 return "Q (Quadword integer)";
6874 case DSC__K_DTYPE_F:
6875 return "F (Single-precision floating)";
6876 case DSC__K_DTYPE_D:
6877 return "D (Double-precision floating)";
6878 case DSC__K_DTYPE_FC:
6879 return "FC (Complex)";
6880 case DSC__K_DTYPE_DC:
6881 return "DC (Double-precision Complex)";
6882 case DSC__K_DTYPE_T:
6883 return "T (ASCII text string)";
6884 case DSC__K_DTYPE_NU:
6885 return "NU (Numeric string, unsigned)";
6886 case DSC__K_DTYPE_NL:
6887 return "NL (Numeric string, left separate sign)";
6888 case DSC__K_DTYPE_NLO:
6889 return "NLO (Numeric string, left overpunched sign)";
6890 case DSC__K_DTYPE_NR:
6891 return "NR (Numeric string, right separate sign)";
6892 case DSC__K_DTYPE_NRO:
6893 return "NRO (Numeric string, right overpunched sig)";
6894 case DSC__K_DTYPE_NZ:
6895 return "NZ (Numeric string, zoned sign)";
6896 case DSC__K_DTYPE_P:
6897 return "P (Packed decimal string)";
6898 case DSC__K_DTYPE_ZI:
6899 return "ZI (Sequence of instructions)";
6900 case DSC__K_DTYPE_ZEM:
6901 return "ZEM (Procedure entry mask)";
6902 case DSC__K_DTYPE_DSC:
6903 return "DSC (Descriptor, used for arrays of dyn strings)";
6904 case DSC__K_DTYPE_OU:
6905 return "OU (Octaword logical)";
6906 case DSC__K_DTYPE_O:
6907 return "O (Octaword integer)";
6908 case DSC__K_DTYPE_G:
6909 return "G (Double precision G floating, 64 bit)";
6910 case DSC__K_DTYPE_H:
6911 return "H (Quadruple precision floating, 128 bit)";
6912 case DSC__K_DTYPE_GC:
6913 return "GC (Double precision complex, G floating)";
6914 case DSC__K_DTYPE_HC:
6915 return "HC (Quadruple precision complex, H floating)";
6916 case DSC__K_DTYPE_CIT:
6917 return "CIT (COBOL intermediate temporary)";
6918 case DSC__K_DTYPE_BPV:
6919 return "BPV (Bound Procedure Value)";
6920 case DSC__K_DTYPE_BLV:
6921 return "BLV (Bound Label Value)";
6922 case DSC__K_DTYPE_VU:
6923 return "VU (Bit Unaligned)";
6924 case DSC__K_DTYPE_ADT:
6925 return "ADT (Absolute Date-Time)";
6926 case DSC__K_DTYPE_VT:
6927 return "VT (Varying Text)";
6928 case DSC__K_DTYPE_T2:
6929 return "T2 (16-bit char)";
6930 case DSC__K_DTYPE_VT2:
6931 return "VT2 (16-bit varying char)";
6932 default:
6933 return "?? (unknown)";
6934 }
6935}
6936
6937static void
6938evax_bfd_print_desc (const unsigned char *buf, int indent, FILE *file)
6939{
6940 unsigned char bclass = buf[3];
6941 unsigned char dtype = buf[2];
6942 unsigned int len = (unsigned)bfd_getl16 (buf);
6943 unsigned int pointer = (unsigned)bfd_getl32 (buf + 4);
6944
6945 evax_bfd_print_indent (indent, file);
6946
6947 if (len == 1 && pointer == 0xffffffffUL)
6948 {
6949 /* 64 bits. */
6950 fprintf (file, _("64 bits *unhandled*\n"));
6951 }
6952 else
6953 {
695344c0 6954 /* xgettext:c-format */
95e34ef7 6955 fprintf (file, _("class: %u, dtype: %u, length: %u, pointer: 0x%08x\n"),
07d6d2b8 6956 bclass, dtype, len, pointer);
95e34ef7 6957 switch (bclass)
07d6d2b8
AM
6958 {
6959 case DSC__K_CLASS_NCA:
6960 {
6961 const struct vms_dsc_nca *dsc = (const void *)buf;
6962 unsigned int i;
6963 const unsigned char *b;
6964
6965 evax_bfd_print_indent (indent, file);
6966 fprintf (file, _("non-contiguous array of %s\n"),
6967 evax_bfd_get_dsc_name (dsc->dtype));
6968 evax_bfd_print_indent (indent + 1, file);
6969 fprintf (file,
695344c0 6970 /* xgettext:c-format */
07d6d2b8
AM
6971 _("dimct: %u, aflags: 0x%02x, digits: %u, scale: %u\n"),
6972 dsc->dimct, dsc->aflags, dsc->digits, dsc->scale);
6973 evax_bfd_print_indent (indent + 1, file);
6974 fprintf (file,
695344c0 6975 /* xgettext:c-format */
07d6d2b8
AM
6976 _("arsize: %u, a0: 0x%08x\n"),
6977 (unsigned)bfd_getl32 (dsc->arsize),
6978 (unsigned)bfd_getl32 (dsc->a0));
6979 evax_bfd_print_indent (indent + 1, file);
6980 fprintf (file, _("Strides:\n"));
6981 b = buf + sizeof (*dsc);
6982 for (i = 0; i < dsc->dimct; i++)
6983 {
6984 evax_bfd_print_indent (indent + 2, file);
6985 fprintf (file, "[%u]: %u\n", i + 1,
6986 (unsigned)bfd_getl32 (b));
6987 b += 4;
6988 }
6989 evax_bfd_print_indent (indent + 1, file);
6990 fprintf (file, _("Bounds:\n"));
6991 b = buf + sizeof (*dsc);
6992 for (i = 0; i < dsc->dimct; i++)
6993 {
6994 evax_bfd_print_indent (indent + 2, file);
695344c0 6995 /* xgettext:c-format */
07d6d2b8
AM
6996 fprintf (file, _("[%u]: Lower: %u, upper: %u\n"), i + 1,
6997 (unsigned)bfd_getl32 (b + 0),
6998 (unsigned)bfd_getl32 (b + 4));
6999 b += 8;
7000 }
7001 }
7002 break;
7003 case DSC__K_CLASS_UBS:
7004 {
7005 const struct vms_dsc_ubs *ubs = (const void *)buf;
7006
7007 evax_bfd_print_indent (indent, file);
7008 fprintf (file, _("unaligned bit-string of %s\n"),
7009 evax_bfd_get_dsc_name (ubs->dtype));
7010 evax_bfd_print_indent (indent + 1, file);
7011 fprintf (file,
695344c0 7012 /* xgettext:c-format */
07d6d2b8
AM
7013 _("base: %u, pos: %u\n"),
7014 (unsigned)bfd_getl32 (ubs->base),
7015 (unsigned)bfd_getl32 (ubs->pos));
7016 }
7017 break;
7018 default:
7019 fprintf (file, _("*unhandled*\n"));
7020 break;
7021 }
95e34ef7
TG
7022 }
7023}
7024
7025static unsigned int
7026evax_bfd_print_valspec (const unsigned char *buf, int indent, FILE *file)
7027{
7028 unsigned int vflags = buf[0];
7029 unsigned int value = (unsigned)bfd_getl32 (buf + 1);
7030 unsigned int len = 5;
7031
7032 evax_bfd_print_indent (indent, file);
695344c0 7033 /* xgettext:c-format */
95e34ef7
TG
7034 fprintf (file, _("vflags: 0x%02x, value: 0x%08x "), vflags, value);
7035 buf += 5;
7036
7037 switch (vflags)
7038 {
7039 case DST__K_VFLAGS_NOVAL:
7040 fprintf (file, _("(no value)\n"));
7041 break;
7042 case DST__K_VFLAGS_NOTACTIVE:
7043 fprintf (file, _("(not active)\n"));
7044 break;
7045 case DST__K_VFLAGS_UNALLOC:
7046 fprintf (file, _("(not allocated)\n"));
7047 break;
7048 case DST__K_VFLAGS_DSC:
7049 fprintf (file, _("(descriptor)\n"));
7050 evax_bfd_print_desc (buf + value, indent + 1, file);
7051 break;
7052 case DST__K_VFLAGS_TVS:
7053 fprintf (file, _("(trailing value)\n"));
7054 break;
7055 case DST__K_VS_FOLLOWS:
7056 fprintf (file, _("(value spec follows)\n"));
7057 break;
7058 case DST__K_VFLAGS_BITOFFS:
7059 fprintf (file, _("(at bit offset %u)\n"), value);
7060 break;
7061 default:
695344c0 7062 /* xgettext:c-format */
95e34ef7 7063 fprintf (file, _("(reg: %u, disp: %u, indir: %u, kind: "),
07d6d2b8
AM
7064 (vflags & DST__K_REGNUM_MASK) >> DST__K_REGNUM_SHIFT,
7065 vflags & DST__K_DISP ? 1 : 0,
7066 vflags & DST__K_INDIR ? 1 : 0);
95e34ef7 7067 switch (vflags & DST__K_VALKIND_MASK)
07d6d2b8
AM
7068 {
7069 case DST__K_VALKIND_LITERAL:
7070 fputs (_("literal"), file);
7071 break;
7072 case DST__K_VALKIND_ADDR:
7073 fputs (_("address"), file);
7074 break;
7075 case DST__K_VALKIND_DESC:
7076 fputs (_("desc"), file);
7077 break;
7078 case DST__K_VALKIND_REG:
7079 fputs (_("reg"), file);
7080 break;
7081 }
95e34ef7
TG
7082 fputs (")\n", file);
7083 break;
7084 }
7085 return len;
7086}
7087
7088static void
7089evax_bfd_print_typspec (const unsigned char *buf, int indent, FILE *file)
7090{
7091 unsigned char kind = buf[2];
7092 unsigned int len = (unsigned)bfd_getl16 (buf);
7093
7094 evax_bfd_print_indent (indent, file);
695344c0
NC
7095 /* xgettext:c-format */
7096 fprintf (file, _("len: %2u, kind: %2u "), len, kind);
95e34ef7
TG
7097 buf += 3;
7098 switch (kind)
7099 {
7100 case DST__K_TS_ATOM:
695344c0
NC
7101 /* xgettext:c-format */
7102 fprintf (file, _("atomic, type=0x%02x %s\n"),
07d6d2b8 7103 buf[0], evax_bfd_get_dsc_name (buf[0]));
95e34ef7
TG
7104 break;
7105 case DST__K_TS_IND:
695344c0 7106 fprintf (file, _("indirect, defined at 0x%08x\n"),
07d6d2b8 7107 (unsigned)bfd_getl32 (buf));
95e34ef7
TG
7108 break;
7109 case DST__K_TS_TPTR:
695344c0 7110 fprintf (file, _("typed pointer\n"));
95e34ef7
TG
7111 evax_bfd_print_typspec (buf, indent + 1, file);
7112 break;
7113 case DST__K_TS_PTR:
695344c0 7114 fprintf (file, _("pointer\n"));
95e34ef7
TG
7115 break;
7116 case DST__K_TS_ARRAY:
7117 {
07d6d2b8
AM
7118 const unsigned char *vs;
7119 unsigned int vec_len;
7120 unsigned int i;
7121
7122 fprintf (file, _("array, dim: %u, bitmap: "), buf[0]);
7123 vec_len = (buf[0] + 1 + 7) / 8;
7124 for (i = 0; i < vec_len; i++)
7125 fprintf (file, " %02x", buf[i + 1]);
7126 fputc ('\n', file);
7127 vs = buf + 1 + vec_len;
7128 evax_bfd_print_indent (indent, file);
7129 fprintf (file, _("array descriptor:\n"));
7130 vs += evax_bfd_print_valspec (vs, indent + 1, file);
7131 for (i = 0; i < buf[0] + 1U; i++)
7132 if (buf[1 + i / 8] & (1 << (i % 8)))
7133 {
7134 evax_bfd_print_indent (indent, file);
7135 if (i == 0)
7136 fprintf (file, _("type spec for element:\n"));
7137 else
7138 fprintf (file, _("type spec for subscript %u:\n"), i);
7139 evax_bfd_print_typspec (vs, indent + 1, file);
7140 vs += bfd_getl16 (vs);
7141 }
95e34ef7
TG
7142 }
7143 break;
7144 default:
695344c0 7145 fprintf (file, _("*unhandled*\n"));
95e34ef7
TG
7146 }
7147}
7148
7149static void
7150evax_bfd_print_dst (struct bfd *abfd, unsigned int dst_size, FILE *file)
7151{
7152 unsigned int off = 0;
7153 unsigned int pc = 0;
7154 unsigned int line = 0;
7155
7156 fprintf (file, _("Debug symbol table:\n"));
7157
7158 while (dst_size > 0)
7159 {
7160 struct vms_dst_header dsth;
7161 unsigned int len;
7162 unsigned int type;
7163 unsigned char *buf;
7164
7165 if (bfd_bread (&dsth, sizeof (dsth), abfd) != sizeof (dsth))
07d6d2b8
AM
7166 {
7167 fprintf (file, _("cannot read DST header\n"));
7168 return;
7169 }
95e34ef7
TG
7170 len = bfd_getl16 (dsth.length);
7171 type = bfd_getl16 (dsth.type);
695344c0 7172 /* xgettext:c-format */
95e34ef7 7173 fprintf (file, _(" type: %3u, len: %3u (at 0x%08x): "),
07d6d2b8 7174 type, len, off);
95e34ef7 7175 if (len == 0)
07d6d2b8
AM
7176 {
7177 fputc ('\n', file);
7178 break;
7179 }
95e34ef7
TG
7180 len++;
7181 dst_size -= len;
7182 off += len;
7183 len -= sizeof (dsth);
2bb3687b
AM
7184 buf = _bfd_malloc_and_read (abfd, len, len);
7185 if (buf == NULL)
07d6d2b8
AM
7186 {
7187 fprintf (file, _("cannot read DST symbol\n"));
7188 return;
7189 }
95e34ef7 7190 switch (type)
07d6d2b8
AM
7191 {
7192 case DSC__K_DTYPE_V:
7193 case DSC__K_DTYPE_BU:
7194 case DSC__K_DTYPE_WU:
7195 case DSC__K_DTYPE_LU:
7196 case DSC__K_DTYPE_QU:
7197 case DSC__K_DTYPE_B:
7198 case DSC__K_DTYPE_W:
7199 case DSC__K_DTYPE_L:
7200 case DSC__K_DTYPE_Q:
7201 case DSC__K_DTYPE_F:
7202 case DSC__K_DTYPE_D:
7203 case DSC__K_DTYPE_FC:
7204 case DSC__K_DTYPE_DC:
7205 case DSC__K_DTYPE_T:
7206 case DSC__K_DTYPE_NU:
7207 case DSC__K_DTYPE_NL:
7208 case DSC__K_DTYPE_NLO:
7209 case DSC__K_DTYPE_NR:
7210 case DSC__K_DTYPE_NRO:
7211 case DSC__K_DTYPE_NZ:
7212 case DSC__K_DTYPE_P:
7213 case DSC__K_DTYPE_ZI:
7214 case DSC__K_DTYPE_ZEM:
7215 case DSC__K_DTYPE_DSC:
7216 case DSC__K_DTYPE_OU:
7217 case DSC__K_DTYPE_O:
7218 case DSC__K_DTYPE_G:
7219 case DSC__K_DTYPE_H:
7220 case DSC__K_DTYPE_GC:
7221 case DSC__K_DTYPE_HC:
7222 case DSC__K_DTYPE_CIT:
7223 case DSC__K_DTYPE_BPV:
7224 case DSC__K_DTYPE_BLV:
7225 case DSC__K_DTYPE_VU:
7226 case DSC__K_DTYPE_ADT:
7227 case DSC__K_DTYPE_VT:
7228 case DSC__K_DTYPE_T2:
7229 case DSC__K_DTYPE_VT2:
7230 fprintf (file, _("standard data: %s\n"),
7231 evax_bfd_get_dsc_name (type));
7232 evax_bfd_print_valspec (buf, 4, file);
7233 fprintf (file, _(" name: %.*s\n"), buf[5], buf + 6);
7234 break;
7235 case DST__K_MODBEG:
7236 {
7237 struct vms_dst_modbeg *dst = (void *)buf;
7238 const char *name = (const char *)buf + sizeof (*dst);
7239
7240 fprintf (file, _("modbeg\n"));
695344c0 7241 /* xgettext:c-format */
07d6d2b8
AM
7242 fprintf (file, _(" flags: %d, language: %u, "
7243 "major: %u, minor: %u\n"),
7244 dst->flags,
7245 (unsigned)bfd_getl32 (dst->language),
7246 (unsigned)bfd_getl16 (dst->major),
7247 (unsigned)bfd_getl16 (dst->minor));
7248 fprintf (file, _(" module name: %.*s\n"),
7249 name[0], name + 1);
7250 name += name[0] + 1;
7251 fprintf (file, _(" compiler : %.*s\n"),
7252 name[0], name + 1);
7253 }
7254 break;
7255 case DST__K_MODEND:
7256 fprintf (file, _("modend\n"));
7257 break;
7258 case DST__K_RTNBEG:
7259 {
7260 struct vms_dst_rtnbeg *dst = (void *)buf;
7261 const char *name = (const char *)buf + sizeof (*dst);
7262
7263 fputs (_("rtnbeg\n"), file);
695344c0 7264 /* xgettext:c-format */
07d6d2b8
AM
7265 fprintf (file, _(" flags: %u, address: 0x%08x, "
7266 "pd-address: 0x%08x\n"),
7267 dst->flags,
7268 (unsigned)bfd_getl32 (dst->address),
7269 (unsigned)bfd_getl32 (dst->pd_address));
7270 fprintf (file, _(" routine name: %.*s\n"),
7271 name[0], name + 1);
7272 }
7273 break;
7274 case DST__K_RTNEND:
7275 {
7276 struct vms_dst_rtnend *dst = (void *)buf;
7277
7278 fprintf (file, _("rtnend: size 0x%08x\n"),
7279 (unsigned)bfd_getl32 (dst->size));
7280 }
7281 break;
7282 case DST__K_PROLOG:
7283 {
7284 struct vms_dst_prolog *dst = (void *)buf;
7285
7286 fprintf (file, _("prolog: bkpt address 0x%08x\n"),
7287 (unsigned)bfd_getl32 (dst->bkpt_addr));
7288 }
7289 break;
7290 case DST__K_EPILOG:
7291 {
7292 struct vms_dst_epilog *dst = (void *)buf;
95e34ef7 7293
695344c0 7294 /* xgettext:c-format */
07d6d2b8
AM
7295 fprintf (file, _("epilog: flags: %u, count: %u\n"),
7296 dst->flags, (unsigned)bfd_getl32 (dst->count));
7297 }
7298 break;
7299 case DST__K_BLKBEG:
7300 {
7301 struct vms_dst_blkbeg *dst = (void *)buf;
7302 const char *name = (const char *)buf + sizeof (*dst);
95e34ef7 7303
695344c0 7304 /* xgettext:c-format */
07d6d2b8
AM
7305 fprintf (file, _("blkbeg: address: 0x%08x, name: %.*s\n"),
7306 (unsigned)bfd_getl32 (dst->address),
7307 name[0], name + 1);
7308 }
7309 break;
7310 case DST__K_BLKEND:
7311 {
7312 struct vms_dst_blkend *dst = (void *)buf;
7313
7314 fprintf (file, _("blkend: size: 0x%08x\n"),
7315 (unsigned)bfd_getl32 (dst->size));
7316 }
7317 break;
7318 case DST__K_TYPSPEC:
7319 {
7320 fprintf (file, _("typspec (len: %u)\n"), len);
7321 fprintf (file, _(" name: %.*s\n"), buf[0], buf + 1);
7322 evax_bfd_print_typspec (buf + 1 + buf[0], 5, file);
7323 }
7324 break;
7325 case DST__K_SEPTYP:
7326 {
7327 fprintf (file, _("septyp, name: %.*s\n"), buf[5], buf + 6);
7328 evax_bfd_print_valspec (buf, 4, file);
7329 }
7330 break;
7331 case DST__K_RECBEG:
7332 {
7333 struct vms_dst_recbeg *recbeg = (void *)buf;
7334 const char *name = (const char *)buf + sizeof (*recbeg);
7335
7336 fprintf (file, _("recbeg: name: %.*s\n"), name[0], name + 1);
7337 evax_bfd_print_valspec (buf, 4, file);
7338 fprintf (file, _(" len: %u bits\n"),
7339 (unsigned)bfd_getl32 (name + 1 + name[0]));
7340 }
7341 break;
7342 case DST__K_RECEND:
7343 fprintf (file, _("recend\n"));
7344 break;
7345 case DST__K_ENUMBEG:
695344c0 7346 /* xgettext:c-format */
07d6d2b8
AM
7347 fprintf (file, _("enumbeg, len: %u, name: %.*s\n"),
7348 buf[0], buf[1], buf + 2);
7349 break;
7350 case DST__K_ENUMELT:
7351 fprintf (file, _("enumelt, name: %.*s\n"), buf[5], buf + 6);
7352 evax_bfd_print_valspec (buf, 4, file);
7353 break;
7354 case DST__K_ENUMEND:
7355 fprintf (file, _("enumend\n"));
7356 break;
7357 case DST__K_LABEL:
7358 {
7359 struct vms_dst_label *lab = (void *)buf;
7360 fprintf (file, _("label, name: %.*s\n"),
7361 lab->name[0], lab->name + 1);
7362 fprintf (file, _(" address: 0x%08x\n"),
7363 (unsigned)bfd_getl32 (lab->value));
7364 }
7365 break;
7366 case DST__K_DIS_RANGE:
7367 {
7368 unsigned int cnt = bfd_getl32 (buf);
7369 unsigned char *rng = buf + 4;
7370 unsigned int i;
7371
7372 fprintf (file, _("discontiguous range (nbr: %u)\n"), cnt);
7373 for (i = 0; i < cnt; i++, rng += 8)
695344c0 7374 /* xgettext:c-format */
07d6d2b8
AM
7375 fprintf (file, _(" address: 0x%08x, size: %u\n"),
7376 (unsigned)bfd_getl32 (rng),
7377 (unsigned)bfd_getl32 (rng + 4));
7378
7379 }
7380 break;
7381 case DST__K_LINE_NUM:
7382 {
7383 unsigned char *buf_orig = buf;
7384
7385 fprintf (file, _("line num (len: %u)\n"), len);
7386
7387 while (len > 0)
7388 {
7389 signed char cmd;
7390 unsigned char cmdlen;
7391 unsigned int val;
7392
7393 cmd = buf[0];
7394 cmdlen = 0;
7395
7396 fputs (" ", file);
7397
7398 switch (cmd)
7399 {
7400 case DST__K_DELTA_PC_W:
7401 val = bfd_getl16 (buf + 1);
7402 fprintf (file, _("delta_pc_w %u\n"), val);
7403 pc += val;
7404 line++;
7405 cmdlen = 3;
7406 break;
7407 case DST__K_INCR_LINUM:
7408 val = buf[1];
7409 fprintf (file, _("incr_linum(b): +%u\n"), val);
7410 line += val;
7411 cmdlen = 2;
7412 break;
7413 case DST__K_INCR_LINUM_W:
7414 val = bfd_getl16 (buf + 1);
7415 fprintf (file, _("incr_linum_w: +%u\n"), val);
7416 line += val;
7417 cmdlen = 3;
7418 break;
7419 case DST__K_INCR_LINUM_L:
7420 val = bfd_getl32 (buf + 1);
7421 fprintf (file, _("incr_linum_l: +%u\n"), val);
7422 line += val;
7423 cmdlen = 5;
7424 break;
7425 case DST__K_SET_LINUM:
7426 line = bfd_getl16 (buf + 1);
7427 fprintf (file, _("set_line_num(w) %u\n"), line);
7428 cmdlen = 3;
7429 break;
7430 case DST__K_SET_LINUM_B:
7431 line = buf[1];
7432 fprintf (file, _("set_line_num_b %u\n"), line);
7433 cmdlen = 2;
7434 break;
7435 case DST__K_SET_LINUM_L:
7436 line = bfd_getl32 (buf + 1);
7437 fprintf (file, _("set_line_num_l %u\n"), line);
7438 cmdlen = 5;
7439 break;
7440 case DST__K_SET_ABS_PC:
7441 pc = bfd_getl32 (buf + 1);
7442 fprintf (file, _("set_abs_pc: 0x%08x\n"), pc);
7443 cmdlen = 5;
7444 break;
7445 case DST__K_DELTA_PC_L:
7446 fprintf (file, _("delta_pc_l: +0x%08x\n"),
7447 (unsigned)bfd_getl32 (buf + 1));
7448 cmdlen = 5;
7449 break;
7450 case DST__K_TERM:
7451 fprintf (file, _("term(b): 0x%02x"), buf[1]);
7452 pc += buf[1];
7453 fprintf (file, _(" pc: 0x%08x\n"), pc);
7454 cmdlen = 2;
7455 break;
7456 case DST__K_TERM_W:
7457 val = bfd_getl16 (buf + 1);
7458 fprintf (file, _("term_w: 0x%04x"), val);
7459 pc += val;
7460 fprintf (file, _(" pc: 0x%08x\n"), pc);
7461 cmdlen = 3;
7462 break;
7463 default:
7464 if (cmd <= 0)
7465 {
7466 fprintf (file, _("delta pc +%-4d"), -cmd);
7467 line++; /* FIXME: curr increment. */
7468 pc += -cmd;
695344c0 7469 /* xgettext:c-format */
07d6d2b8
AM
7470 fprintf (file, _(" pc: 0x%08x line: %5u\n"),
7471 pc, line);
7472 cmdlen = 1;
7473 }
7474 else
7475 fprintf (file, _(" *unhandled* cmd %u\n"), cmd);
7476 break;
7477 }
7478 if (cmdlen == 0)
7479 break;
7480 len -= cmdlen;
7481 buf += cmdlen;
7482 }
7483 buf = buf_orig;
7484 }
7485 break;
7486 case DST__K_SOURCE:
7487 {
7488 unsigned char *buf_orig = buf;
7489
7490 fprintf (file, _("source (len: %u)\n"), len);
7491
7492 while (len > 0)
7493 {
7494 signed char cmd = buf[0];
7495 unsigned char cmdlen = 0;
7496
7497 switch (cmd)
7498 {
7499 case DST__K_SRC_DECLFILE:
7500 {
7501 struct vms_dst_src_decl_src *src = (void *)(buf + 1);
7502 const char *name;
95e34ef7 7503
695344c0 7504 /* xgettext:c-format */
07d6d2b8
AM
7505 fprintf (file, _(" declfile: len: %u, flags: %u, "
7506 "fileid: %u\n"),
7507 src->length, src->flags,
7508 (unsigned)bfd_getl16 (src->fileid));
695344c0 7509 /* xgettext:c-format */
07d6d2b8
AM
7510 fprintf (file, _(" rms: cdt: 0x%08x %08x, "
7511 "ebk: 0x%08x, ffb: 0x%04x, "
7512 "rfo: %u\n"),
7513 (unsigned)bfd_getl32 (src->rms_cdt + 4),
7514 (unsigned)bfd_getl32 (src->rms_cdt + 0),
7515 (unsigned)bfd_getl32 (src->rms_ebk),
7516 (unsigned)bfd_getl16 (src->rms_ffb),
7517 src->rms_rfo);
7518 name = (const char *)buf + 1 + sizeof (*src);
7519 fprintf (file, _(" filename : %.*s\n"),
7520 name[0], name + 1);
7521 name += name[0] + 1;
7522 fprintf (file, _(" module name: %.*s\n"),
7523 name[0], name + 1);
7524 cmdlen = 2 + src->length;
7525 }
7526 break;
7527 case DST__K_SRC_SETFILE:
7528 fprintf (file, _(" setfile %u\n"),
7529 (unsigned)bfd_getl16 (buf + 1));
7530 cmdlen = 3;
7531 break;
7532 case DST__K_SRC_SETREC_W:
7533 fprintf (file, _(" setrec %u\n"),
7534 (unsigned)bfd_getl16 (buf + 1));
7535 cmdlen = 3;
7536 break;
7537 case DST__K_SRC_SETREC_L:
7538 fprintf (file, _(" setrec %u\n"),
7539 (unsigned)bfd_getl32 (buf + 1));
7540 cmdlen = 5;
7541 break;
7542 case DST__K_SRC_SETLNUM_W:
7543 fprintf (file, _(" setlnum %u\n"),
7544 (unsigned)bfd_getl16 (buf + 1));
7545 cmdlen = 3;
7546 break;
7547 case DST__K_SRC_SETLNUM_L:
7548 fprintf (file, _(" setlnum %u\n"),
7549 (unsigned)bfd_getl32 (buf + 1));
7550 cmdlen = 5;
7551 break;
7552 case DST__K_SRC_DEFLINES_W:
7553 fprintf (file, _(" deflines %u\n"),
7554 (unsigned)bfd_getl16 (buf + 1));
7555 cmdlen = 3;
7556 break;
7557 case DST__K_SRC_DEFLINES_B:
7558 fprintf (file, _(" deflines %u\n"), buf[1]);
7559 cmdlen = 2;
7560 break;
7561 case DST__K_SRC_FORMFEED:
7562 fprintf (file, _(" formfeed\n"));
7563 cmdlen = 1;
7564 break;
7565 default:
7566 fprintf (file, _(" *unhandled* cmd %u\n"), cmd);
7567 break;
7568 }
7569 if (cmdlen == 0)
7570 break;
7571 len -= cmdlen;
7572 buf += cmdlen;
7573 }
7574 buf = buf_orig;
7575 }
7576 break;
7577 default:
7578 fprintf (file, _("*unhandled* dst type %u\n"), type);
7579 break;
7580 }
95e34ef7
TG
7581 free (buf);
7582 }
7583}
7584
7585static void
7586evax_bfd_print_image (bfd *abfd, FILE *file)
7587{
7588 struct vms_eihd eihd;
7589 const char *name;
7590 unsigned int val;
7591 unsigned int eiha_off;
7592 unsigned int eihi_off;
7593 unsigned int eihs_off;
7594 unsigned int eisd_off;
7595 unsigned int eihef_off = 0;
7596 unsigned int eihnp_off = 0;
7597 unsigned int dmt_vbn = 0;
7598 unsigned int dmt_size = 0;
7599 unsigned int dst_vbn = 0;
7600 unsigned int dst_size = 0;
7601 unsigned int gst_vbn = 0;
7602 unsigned int gst_size = 0;
7603 unsigned int eiaf_vbn = 0;
7604 unsigned int eiaf_size = 0;
7605 unsigned int eihvn_off;
7606
7607 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET)
7608 || bfd_bread (&eihd, sizeof (eihd), abfd) != sizeof (eihd))
7609 {
7610 fprintf (file, _("cannot read EIHD\n"));
7611 return;
7612 }
695344c0 7613 /* xgettext:c-format */
95e34ef7 7614 fprintf (file, _("EIHD: (size: %u, nbr blocks: %u)\n"),
07d6d2b8
AM
7615 (unsigned)bfd_getl32 (eihd.size),
7616 (unsigned)bfd_getl32 (eihd.hdrblkcnt));
695344c0 7617 /* xgettext:c-format */
95e34ef7 7618 fprintf (file, _(" majorid: %u, minorid: %u\n"),
07d6d2b8
AM
7619 (unsigned)bfd_getl32 (eihd.majorid),
7620 (unsigned)bfd_getl32 (eihd.minorid));
95e34ef7
TG
7621
7622 val = (unsigned)bfd_getl32 (eihd.imgtype);
7623 switch (val)
7624 {
7625 case EIHD__K_EXE:
7626 name = _("executable");
7627 break;
7628 case EIHD__K_LIM:
7629 name = _("linkable image");
7630 break;
7631 default:
7632 name = _("unknown");
7633 break;
7634 }
695344c0 7635 /* xgettext:c-format */
95e34ef7
TG
7636 fprintf (file, _(" image type: %u (%s)"), val, name);
7637
7638 val = (unsigned)bfd_getl32 (eihd.subtype);
7639 switch (val)
7640 {
7641 case EIHD__C_NATIVE:
7642 name = _("native");
7643 break;
7644 case EIHD__C_CLI:
7645 name = _("CLI");
7646 break;
7647 default:
7648 name = _("unknown");
7649 break;
7650 }
695344c0 7651 /* xgettext:c-format */
95e34ef7
TG
7652 fprintf (file, _(", subtype: %u (%s)\n"), val, name);
7653
7654 eisd_off = bfd_getl32 (eihd.isdoff);
7655 eiha_off = bfd_getl32 (eihd.activoff);
7656 eihi_off = bfd_getl32 (eihd.imgidoff);
7657 eihs_off = bfd_getl32 (eihd.symdbgoff);
695344c0 7658 /* xgettext:c-format */
95e34ef7 7659 fprintf (file, _(" offsets: isd: %u, activ: %u, symdbg: %u, "
07d6d2b8
AM
7660 "imgid: %u, patch: %u\n"),
7661 eisd_off, eiha_off, eihs_off, eihi_off,
7662 (unsigned)bfd_getl32 (eihd.patchoff));
95e34ef7
TG
7663 fprintf (file, _(" fixup info rva: "));
7664 bfd_fprintf_vma (abfd, file, bfd_getl64 (eihd.iafva));
7665 fprintf (file, _(", symbol vector rva: "));
7666 bfd_fprintf_vma (abfd, file, bfd_getl64 (eihd.symvva));
7667 eihvn_off = bfd_getl32 (eihd.version_array_off);
7668 fprintf (file, _("\n"
07d6d2b8
AM
7669 " version array off: %u\n"),
7670 eihvn_off);
95e34ef7 7671 fprintf (file,
695344c0 7672 /* xgettext:c-format */
07d6d2b8
AM
7673 _(" img I/O count: %u, nbr channels: %u, req pri: %08x%08x\n"),
7674 (unsigned)bfd_getl32 (eihd.imgiocnt),
7675 (unsigned)bfd_getl32 (eihd.iochancnt),
7676 (unsigned)bfd_getl32 (eihd.privreqs + 4),
7677 (unsigned)bfd_getl32 (eihd.privreqs + 0));
95e34ef7
TG
7678 val = (unsigned)bfd_getl32 (eihd.lnkflags);
7679 fprintf (file, _(" linker flags: %08x:"), val);
7680 if (val & EIHD__M_LNKDEBUG)
7681 fprintf (file, " LNKDEBUG");
7682 if (val & EIHD__M_LNKNOTFR)
7683 fprintf (file, " LNKNOTFR");
7684 if (val & EIHD__M_NOP0BUFS)
7685 fprintf (file, " NOP0BUFS");
7686 if (val & EIHD__M_PICIMG)
7687 fprintf (file, " PICIMG");
7688 if (val & EIHD__M_P0IMAGE)
7689 fprintf (file, " P0IMAGE");
7690 if (val & EIHD__M_DBGDMT)
7691 fprintf (file, " DBGDMT");
7692 if (val & EIHD__M_INISHR)
7693 fprintf (file, " INISHR");
7694 if (val & EIHD__M_XLATED)
7695 fprintf (file, " XLATED");
7696 if (val & EIHD__M_BIND_CODE_SEC)
7697 fprintf (file, " BIND_CODE_SEC");
7698 if (val & EIHD__M_BIND_DATA_SEC)
7699 fprintf (file, " BIND_DATA_SEC");
7700 if (val & EIHD__M_MKTHREADS)
7701 fprintf (file, " MKTHREADS");
7702 if (val & EIHD__M_UPCALLS)
7703 fprintf (file, " UPCALLS");
7704 if (val & EIHD__M_OMV_READY)
7705 fprintf (file, " OMV_READY");
7706 if (val & EIHD__M_EXT_BIND_SECT)
7707 fprintf (file, " EXT_BIND_SECT");
7708 fprintf (file, "\n");
695344c0 7709 /* xgettext:c-format */
95e34ef7 7710 fprintf (file, _(" ident: 0x%08x, sysver: 0x%08x, "
07d6d2b8
AM
7711 "match ctrl: %u, symvect_size: %u\n"),
7712 (unsigned)bfd_getl32 (eihd.ident),
7713 (unsigned)bfd_getl32 (eihd.sysver),
7714 eihd.matchctl,
7715 (unsigned)bfd_getl32 (eihd.symvect_size));
95e34ef7 7716 fprintf (file, _(" BPAGE: %u"),
07d6d2b8 7717 (unsigned)bfd_getl32 (eihd.virt_mem_block_size));
95e34ef7
TG
7718 if (val & (EIHD__M_OMV_READY | EIHD__M_EXT_BIND_SECT))
7719 {
7720 eihef_off = bfd_getl32 (eihd.ext_fixup_off);
7721 eihnp_off = bfd_getl32 (eihd.noopt_psect_off);
695344c0 7722 /* xgettext:c-format */
95e34ef7 7723 fprintf (file, _(", ext fixup offset: %u, no_opt psect off: %u"),
07d6d2b8 7724 eihef_off, eihnp_off);
95e34ef7
TG
7725 }
7726 fprintf (file, _(", alias: %u\n"), (unsigned)bfd_getl16 (eihd.alias));
7727
7728 if (eihvn_off != 0)
7729 {
7730 struct vms_eihvn eihvn;
7731 unsigned int mask;
7732 unsigned int j;
7733
7734 fprintf (file, _("system version array information:\n"));
7735 if (bfd_seek (abfd, (file_ptr) eihvn_off, SEEK_SET)
07d6d2b8
AM
7736 || bfd_bread (&eihvn, sizeof (eihvn), abfd) != sizeof (eihvn))
7737 {
7738 fprintf (file, _("cannot read EIHVN header\n"));
7739 return;
7740 }
95e34ef7
TG
7741 mask = bfd_getl32 (eihvn.subsystem_mask);
7742 for (j = 0; j < 32; j++)
07d6d2b8
AM
7743 if (mask & (1 << j))
7744 {
7745 struct vms_eihvn_subversion ver;
7746 if (bfd_bread (&ver, sizeof (ver), abfd) != sizeof (ver))
7747 {
7748 fprintf (file, _("cannot read EIHVN version\n"));
7749 return;
7750 }
7751 fprintf (file, _(" %02u "), j);
7752 switch (j)
7753 {
7754 case EIHVN__BASE_IMAGE_BIT:
95e34ef7 7755 fputs (_("BASE_IMAGE "), file);
07d6d2b8
AM
7756 break;
7757 case EIHVN__MEMORY_MANAGEMENT_BIT:
7758 fputs (_("MEMORY_MANAGEMENT"), file);
7759 break;
7760 case EIHVN__IO_BIT:
7761 fputs (_("IO "), file);
7762 break;
7763 case EIHVN__FILES_VOLUMES_BIT:
7764 fputs (_("FILES_VOLUMES "), file);
7765 break;
7766 case EIHVN__PROCESS_SCHED_BIT:
7767 fputs (_("PROCESS_SCHED "), file);
7768 break;
7769 case EIHVN__SYSGEN_BIT:
95e34ef7 7770 fputs (_("SYSGEN "), file);
07d6d2b8
AM
7771 break;
7772 case EIHVN__CLUSTERS_LOCKMGR_BIT:
7773 fputs (_("CLUSTERS_LOCKMGR "), file);
7774 break;
7775 case EIHVN__LOGICAL_NAMES_BIT:
7776 fputs (_("LOGICAL_NAMES "), file);
7777 break;
7778 case EIHVN__SECURITY_BIT:
95e34ef7 7779 fputs (_("SECURITY "), file);
07d6d2b8
AM
7780 break;
7781 case EIHVN__IMAGE_ACTIVATOR_BIT:
7782 fputs (_("IMAGE_ACTIVATOR "), file);
7783 break;
7784 case EIHVN__NETWORKS_BIT:
95e34ef7 7785 fputs (_("NETWORKS "), file);
07d6d2b8
AM
7786 break;
7787 case EIHVN__COUNTERS_BIT:
95e34ef7 7788 fputs (_("COUNTERS "), file);
07d6d2b8
AM
7789 break;
7790 case EIHVN__STABLE_BIT:
95e34ef7 7791 fputs (_("STABLE "), file);
07d6d2b8
AM
7792 break;
7793 case EIHVN__MISC_BIT:
7794 fputs (_("MISC "), file);
7795 break;
7796 case EIHVN__CPU_BIT:
7797 fputs (_("CPU "), file);
7798 break;
7799 case EIHVN__VOLATILE_BIT:
95e34ef7 7800 fputs (_("VOLATILE "), file);
07d6d2b8
AM
7801 break;
7802 case EIHVN__SHELL_BIT:
95e34ef7 7803 fputs (_("SHELL "), file);
07d6d2b8
AM
7804 break;
7805 case EIHVN__POSIX_BIT:
95e34ef7 7806 fputs (_("POSIX "), file);
07d6d2b8
AM
7807 break;
7808 case EIHVN__MULTI_PROCESSING_BIT:
7809 fputs (_("MULTI_PROCESSING "), file);
7810 break;
7811 case EIHVN__GALAXY_BIT:
95e34ef7 7812 fputs (_("GALAXY "), file);
07d6d2b8
AM
7813 break;
7814 default:
7815 fputs (_("*unknown* "), file);
7816 break;
7817 }
7818 fprintf (file, ": %u.%u\n",
7819 (unsigned)bfd_getl16 (ver.major),
7820 (unsigned)bfd_getl16 (ver.minor));
7821 }
95e34ef7
TG
7822 }
7823
7824 if (eiha_off != 0)
7825 {
7826 struct vms_eiha eiha;
7827
7828 if (bfd_seek (abfd, (file_ptr) eiha_off, SEEK_SET)
07d6d2b8
AM
7829 || bfd_bread (&eiha, sizeof (eiha), abfd) != sizeof (eiha))
7830 {
7831 fprintf (file, _("cannot read EIHA\n"));
7832 return;
7833 }
95e34ef7 7834 fprintf (file, _("Image activation: (size=%u)\n"),
07d6d2b8 7835 (unsigned)bfd_getl32 (eiha.size));
695344c0 7836 /* xgettext:c-format */
95e34ef7 7837 fprintf (file, _(" First address : 0x%08x 0x%08x\n"),
07d6d2b8
AM
7838 (unsigned)bfd_getl32 (eiha.tfradr1_h),
7839 (unsigned)bfd_getl32 (eiha.tfradr1));
695344c0 7840 /* xgettext:c-format */
95e34ef7 7841 fprintf (file, _(" Second address: 0x%08x 0x%08x\n"),
07d6d2b8
AM
7842 (unsigned)bfd_getl32 (eiha.tfradr2_h),
7843 (unsigned)bfd_getl32 (eiha.tfradr2));
695344c0 7844 /* xgettext:c-format */
95e34ef7 7845 fprintf (file, _(" Third address : 0x%08x 0x%08x\n"),
07d6d2b8
AM
7846 (unsigned)bfd_getl32 (eiha.tfradr3_h),
7847 (unsigned)bfd_getl32 (eiha.tfradr3));
695344c0 7848 /* xgettext:c-format */
95e34ef7 7849 fprintf (file, _(" Fourth address: 0x%08x 0x%08x\n"),
07d6d2b8
AM
7850 (unsigned)bfd_getl32 (eiha.tfradr4_h),
7851 (unsigned)bfd_getl32 (eiha.tfradr4));
695344c0 7852 /* xgettext:c-format */
95e34ef7 7853 fprintf (file, _(" Shared image : 0x%08x 0x%08x\n"),
07d6d2b8
AM
7854 (unsigned)bfd_getl32 (eiha.inishr_h),
7855 (unsigned)bfd_getl32 (eiha.inishr));
95e34ef7
TG
7856 }
7857 if (eihi_off != 0)
7858 {
7859 struct vms_eihi eihi;
7860
7861 if (bfd_seek (abfd, (file_ptr) eihi_off, SEEK_SET)
07d6d2b8
AM
7862 || bfd_bread (&eihi, sizeof (eihi), abfd) != sizeof (eihi))
7863 {
7864 fprintf (file, _("cannot read EIHI\n"));
7865 return;
7866 }
695344c0 7867 /* xgettext:c-format */
95e34ef7 7868 fprintf (file, _("Image identification: (major: %u, minor: %u)\n"),
07d6d2b8
AM
7869 (unsigned)bfd_getl32 (eihi.majorid),
7870 (unsigned)bfd_getl32 (eihi.minorid));
95e34ef7 7871 fprintf (file, _(" image name : %.*s\n"),
07d6d2b8 7872 eihi.imgnam[0], eihi.imgnam + 1);
95e34ef7 7873 fprintf (file, _(" link time : %s\n"),
07d6d2b8 7874 vms_time_to_str (eihi.linktime));
95e34ef7 7875 fprintf (file, _(" image ident : %.*s\n"),
07d6d2b8 7876 eihi.imgid[0], eihi.imgid + 1);
95e34ef7 7877 fprintf (file, _(" linker ident : %.*s\n"),
07d6d2b8 7878 eihi.linkid[0], eihi.linkid + 1);
95e34ef7 7879 fprintf (file, _(" image build ident: %.*s\n"),
07d6d2b8 7880 eihi.imgbid[0], eihi.imgbid + 1);
95e34ef7
TG
7881 }
7882 if (eihs_off != 0)
7883 {
7884 struct vms_eihs eihs;
7885
7886 if (bfd_seek (abfd, (file_ptr) eihs_off, SEEK_SET)
07d6d2b8
AM
7887 || bfd_bread (&eihs, sizeof (eihs), abfd) != sizeof (eihs))
7888 {
7889 fprintf (file, _("cannot read EIHS\n"));
7890 return;
7891 }
695344c0 7892 /* xgettext:c-format */
95e34ef7 7893 fprintf (file, _("Image symbol & debug table: (major: %u, minor: %u)\n"),
07d6d2b8
AM
7894 (unsigned)bfd_getl32 (eihs.majorid),
7895 (unsigned)bfd_getl32 (eihs.minorid));
95e34ef7
TG
7896 dst_vbn = bfd_getl32 (eihs.dstvbn);
7897 dst_size = bfd_getl32 (eihs.dstsize);
695344c0 7898 /* xgettext:c-format */
44273c5b 7899 fprintf (file, _(" debug symbol table : vbn: %u, size: %u (0x%x)\n"),
07d6d2b8 7900 dst_vbn, dst_size, dst_size);
95e34ef7
TG
7901 gst_vbn = bfd_getl32 (eihs.gstvbn);
7902 gst_size = bfd_getl32 (eihs.gstsize);
695344c0 7903 /* xgettext:c-format */
95e34ef7 7904 fprintf (file, _(" global symbol table: vbn: %u, records: %u\n"),
07d6d2b8 7905 gst_vbn, gst_size);
95e34ef7
TG
7906 dmt_vbn = bfd_getl32 (eihs.dmtvbn);
7907 dmt_size = bfd_getl32 (eihs.dmtsize);
695344c0 7908 /* xgettext:c-format */
95e34ef7 7909 fprintf (file, _(" debug module table : vbn: %u, size: %u\n"),
07d6d2b8 7910 dmt_vbn, dmt_size);
95e34ef7
TG
7911 }
7912 while (eisd_off != 0)
7913 {
7914 struct vms_eisd eisd;
7915 unsigned int len;
7916
7917 while (1)
07d6d2b8
AM
7918 {
7919 if (bfd_seek (abfd, (file_ptr) eisd_off, SEEK_SET)
7920 || bfd_bread (&eisd, sizeof (eisd), abfd) != sizeof (eisd))
7921 {
7922 fprintf (file, _("cannot read EISD\n"));
7923 return;
7924 }
7925 len = (unsigned)bfd_getl32 (eisd.eisdsize);
7926 if (len != (unsigned)-1)
7927 break;
7928
7929 /* Next block. */
7930 eisd_off = (eisd_off + VMS_BLOCK_SIZE) & ~(VMS_BLOCK_SIZE - 1);
7931 }
695344c0 7932 /* xgettext:c-format */
95e34ef7 7933 fprintf (file, _("Image section descriptor: (major: %u, minor: %u, "
07d6d2b8
AM
7934 "size: %u, offset: %u)\n"),
7935 (unsigned)bfd_getl32 (eisd.majorid),
7936 (unsigned)bfd_getl32 (eisd.minorid),
7937 len, eisd_off);
95e34ef7 7938 if (len == 0)
07d6d2b8 7939 break;
695344c0 7940 /* xgettext:c-format */
95e34ef7 7941 fprintf (file, _(" section: base: 0x%08x%08x size: 0x%08x\n"),
07d6d2b8
AM
7942 (unsigned)bfd_getl32 (eisd.virt_addr + 4),
7943 (unsigned)bfd_getl32 (eisd.virt_addr + 0),
7944 (unsigned)bfd_getl32 (eisd.secsize));
95e34ef7
TG
7945 val = (unsigned)bfd_getl32 (eisd.flags);
7946 fprintf (file, _(" flags: 0x%04x"), val);
7947 if (val & EISD__M_GBL)
07d6d2b8 7948 fprintf (file, " GBL");
95e34ef7 7949 if (val & EISD__M_CRF)
07d6d2b8 7950 fprintf (file, " CRF");
95e34ef7 7951 if (val & EISD__M_DZRO)
07d6d2b8 7952 fprintf (file, " DZRO");
95e34ef7 7953 if (val & EISD__M_WRT)
07d6d2b8 7954 fprintf (file, " WRT");
95e34ef7
TG
7955 if (val & EISD__M_INITALCODE)
7956 fprintf (file, " INITALCODE");
7957 if (val & EISD__M_BASED)
07d6d2b8 7958 fprintf (file, " BASED");
95e34ef7
TG
7959 if (val & EISD__M_FIXUPVEC)
7960 fprintf (file, " FIXUPVEC");
7961 if (val & EISD__M_RESIDENT)
7962 fprintf (file, " RESIDENT");
7963 if (val & EISD__M_VECTOR)
07d6d2b8 7964 fprintf (file, " VECTOR");
95e34ef7
TG
7965 if (val & EISD__M_PROTECT)
7966 fprintf (file, " PROTECT");
7967 if (val & EISD__M_LASTCLU)
7968 fprintf (file, " LASTCLU");
7969 if (val & EISD__M_EXE)
07d6d2b8 7970 fprintf (file, " EXE");
95e34ef7
TG
7971 if (val & EISD__M_NONSHRADR)
7972 fprintf (file, " NONSHRADR");
7973 if (val & EISD__M_QUAD_LENGTH)
7974 fprintf (file, " QUAD_LENGTH");
7975 if (val & EISD__M_ALLOC_64BIT)
7976 fprintf (file, " ALLOC_64BIT");
7977 fprintf (file, "\n");
7978 if (val & EISD__M_FIXUPVEC)
07d6d2b8
AM
7979 {
7980 eiaf_vbn = bfd_getl32 (eisd.vbn);
7981 eiaf_size = bfd_getl32 (eisd.secsize);
7982 }
695344c0 7983 /* xgettext:c-format */
95e34ef7 7984 fprintf (file, _(" vbn: %u, pfc: %u, matchctl: %u type: %u ("),
07d6d2b8
AM
7985 (unsigned)bfd_getl32 (eisd.vbn),
7986 eisd.pfc, eisd.matchctl, eisd.type);
95e34ef7 7987 switch (eisd.type)
07d6d2b8
AM
7988 {
7989 case EISD__K_NORMAL:
7990 fputs (_("NORMAL"), file);
7991 break;
7992 case EISD__K_SHRFXD:
7993 fputs (_("SHRFXD"), file);
7994 break;
7995 case EISD__K_PRVFXD:
7996 fputs (_("PRVFXD"), file);
7997 break;
7998 case EISD__K_SHRPIC:
7999 fputs (_("SHRPIC"), file);
8000 break;
8001 case EISD__K_PRVPIC:
8002 fputs (_("PRVPIC"), file);
8003 break;
8004 case EISD__K_USRSTACK:
8005 fputs (_("USRSTACK"), file);
8006 break;
8007 default:
8008 fputs (_("*unknown*"), file);
8009 break;
8010 }
95e34ef7
TG
8011 fputs (_(")\n"), file);
8012 if (val & EISD__M_GBL)
695344c0 8013 /* xgettext:c-format */
07d6d2b8
AM
8014 fprintf (file, _(" ident: 0x%08x, name: %.*s\n"),
8015 (unsigned)bfd_getl32 (eisd.ident),
8016 eisd.gblnam[0], eisd.gblnam + 1);
95e34ef7
TG
8017 eisd_off += len;
8018 }
8019
8020 if (dmt_vbn != 0)
8021 {
8022 if (bfd_seek (abfd, (file_ptr) (dmt_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET))
07d6d2b8
AM
8023 {
8024 fprintf (file, _("cannot read DMT\n"));
8025 return;
8026 }
95e34ef7
TG
8027
8028 fprintf (file, _("Debug module table:\n"));
8029
8030 while (dmt_size > 0)
07d6d2b8
AM
8031 {
8032 struct vms_dmt_header dmth;
8033 unsigned int count;
8034
8035 if (bfd_bread (&dmth, sizeof (dmth), abfd) != sizeof (dmth))
8036 {
8037 fprintf (file, _("cannot read DMT header\n"));
8038 return;
8039 }
8040 count = bfd_getl16 (dmth.psect_count);
8041 fprintf (file,
695344c0 8042 /* xgettext:c-format */
07d6d2b8
AM
8043 _(" module offset: 0x%08x, size: 0x%08x, (%u psects)\n"),
8044 (unsigned)bfd_getl32 (dmth.modbeg),
8045 (unsigned)bfd_getl32 (dmth.size), count);
8046 dmt_size -= sizeof (dmth);
8047 while (count > 0)
8048 {
8049 struct vms_dmt_psect dmtp;
8050
8051 if (bfd_bread (&dmtp, sizeof (dmtp), abfd) != sizeof (dmtp))
8052 {
8053 fprintf (file, _("cannot read DMT psect\n"));
8054 return;
8055 }
695344c0 8056 /* xgettext:c-format */
07d6d2b8
AM
8057 fprintf (file, _(" psect start: 0x%08x, length: %u\n"),
8058 (unsigned)bfd_getl32 (dmtp.start),
8059 (unsigned)bfd_getl32 (dmtp.length));
8060 count--;
8061 dmt_size -= sizeof (dmtp);
8062 }
8063 }
95e34ef7
TG
8064 }
8065
8066 if (dst_vbn != 0)
8067 {
8068 if (bfd_seek (abfd, (file_ptr) (dst_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET))
07d6d2b8
AM
8069 {
8070 fprintf (file, _("cannot read DST\n"));
8071 return;
8072 }
95e34ef7
TG
8073
8074 evax_bfd_print_dst (abfd, dst_size, file);
8075 }
8076 if (gst_vbn != 0)
8077 {
8078 if (bfd_seek (abfd, (file_ptr) (gst_vbn - 1) * VMS_BLOCK_SIZE, SEEK_SET))
07d6d2b8
AM
8079 {
8080 fprintf (file, _("cannot read GST\n"));
8081 return;
8082 }
95e34ef7
TG
8083
8084 fprintf (file, _("Global symbol table:\n"));
8085 evax_bfd_print_eobj (abfd, file);
8086 }
8087 if (eiaf_vbn != 0)
8088 {
8089 unsigned char *buf;
8090 struct vms_eiaf *eiaf;
8091 unsigned int qrelfixoff;
8092 unsigned int lrelfixoff;
8093 unsigned int qdotadroff;
8094 unsigned int ldotadroff;
8095 unsigned int shrimgcnt;
8096 unsigned int shlstoff;
8097 unsigned int codeadroff;
8098 unsigned int lpfixoff;
8099 unsigned int chgprtoff;
2bb3687b 8100 file_ptr f_off = (file_ptr) (eiaf_vbn - 1) * VMS_BLOCK_SIZE;
95e34ef7 8101
2bb3687b
AM
8102 if (bfd_seek (abfd, f_off, SEEK_SET) != 0
8103 || (buf = _bfd_malloc_and_read (abfd, eiaf_size, eiaf_size)) == NULL)
07d6d2b8
AM
8104 {
8105 fprintf (file, _("cannot read EIHA\n"));
07d6d2b8
AM
8106 return;
8107 }
95e34ef7
TG
8108 eiaf = (struct vms_eiaf *)buf;
8109 fprintf (file,
695344c0 8110 /* xgettext:c-format */
07d6d2b8
AM
8111 _("Image activator fixup: (major: %u, minor: %u)\n"),
8112 (unsigned)bfd_getl32 (eiaf->majorid),
8113 (unsigned)bfd_getl32 (eiaf->minorid));
695344c0 8114 /* xgettext:c-format */
95e34ef7 8115 fprintf (file, _(" iaflink : 0x%08x %08x\n"),
07d6d2b8
AM
8116 (unsigned)bfd_getl32 (eiaf->iaflink + 0),
8117 (unsigned)bfd_getl32 (eiaf->iaflink + 4));
695344c0 8118 /* xgettext:c-format */
95e34ef7 8119 fprintf (file, _(" fixuplnk: 0x%08x %08x\n"),
07d6d2b8
AM
8120 (unsigned)bfd_getl32 (eiaf->fixuplnk + 0),
8121 (unsigned)bfd_getl32 (eiaf->fixuplnk + 4));
95e34ef7 8122 fprintf (file, _(" size : %u\n"),
07d6d2b8 8123 (unsigned)bfd_getl32 (eiaf->size));
95e34ef7 8124 fprintf (file, _(" flags: 0x%08x\n"),
07d6d2b8 8125 (unsigned)bfd_getl32 (eiaf->flags));
95e34ef7
TG
8126 qrelfixoff = bfd_getl32 (eiaf->qrelfixoff);
8127 lrelfixoff = bfd_getl32 (eiaf->lrelfixoff);
695344c0 8128 /* xgettext:c-format */
95e34ef7 8129 fprintf (file, _(" qrelfixoff: %5u, lrelfixoff: %5u\n"),
07d6d2b8 8130 qrelfixoff, lrelfixoff);
95e34ef7
TG
8131 qdotadroff = bfd_getl32 (eiaf->qdotadroff);
8132 ldotadroff = bfd_getl32 (eiaf->ldotadroff);
695344c0 8133 /* xgettext:c-format */
95e34ef7 8134 fprintf (file, _(" qdotadroff: %5u, ldotadroff: %5u\n"),
07d6d2b8 8135 qdotadroff, ldotadroff);
95e34ef7
TG
8136 codeadroff = bfd_getl32 (eiaf->codeadroff);
8137 lpfixoff = bfd_getl32 (eiaf->lpfixoff);
695344c0 8138 /* xgettext:c-format */
95e34ef7 8139 fprintf (file, _(" codeadroff: %5u, lpfixoff : %5u\n"),
07d6d2b8 8140 codeadroff, lpfixoff);
95e34ef7
TG
8141 chgprtoff = bfd_getl32 (eiaf->chgprtoff);
8142 fprintf (file, _(" chgprtoff : %5u\n"), chgprtoff);
8143 shrimgcnt = bfd_getl32 (eiaf->shrimgcnt);
8144 shlstoff = bfd_getl32 (eiaf->shlstoff);
695344c0 8145 /* xgettext:c-format */
95e34ef7 8146 fprintf (file, _(" shlstoff : %5u, shrimgcnt : %5u\n"),
07d6d2b8 8147 shlstoff, shrimgcnt);
695344c0 8148 /* xgettext:c-format */
95e34ef7 8149 fprintf (file, _(" shlextra : %5u, permctx : %5u\n"),
07d6d2b8
AM
8150 (unsigned)bfd_getl32 (eiaf->shlextra),
8151 (unsigned)bfd_getl32 (eiaf->permctx));
95e34ef7 8152 fprintf (file, _(" base_va : 0x%08x\n"),
07d6d2b8 8153 (unsigned)bfd_getl32 (eiaf->base_va));
95e34ef7 8154 fprintf (file, _(" lppsbfixoff: %5u\n"),
07d6d2b8 8155 (unsigned)bfd_getl32 (eiaf->lppsbfixoff));
95e34ef7
TG
8156
8157 if (shlstoff)
07d6d2b8
AM
8158 {
8159 struct vms_shl *shl = (struct vms_shl *)(buf + shlstoff);
8160 unsigned int j;
8161
8162 fprintf (file, _(" Shareable images:\n"));
8163 for (j = 0; j < shrimgcnt; j++, shl++)
8164 {
8165 fprintf (file,
695344c0 8166 /* xgettext:c-format */
07d6d2b8
AM
8167 _(" %u: size: %u, flags: 0x%02x, name: %.*s\n"),
8168 j, shl->size, shl->flags,
8169 shl->imgnam[0], shl->imgnam + 1);
8170 }
8171 }
95e34ef7 8172 if (qrelfixoff != 0)
07d6d2b8
AM
8173 {
8174 fprintf (file, _(" quad-word relocation fixups:\n"));
8175 evax_bfd_print_relocation_records (file, buf + qrelfixoff, 8);
8176 }
95e34ef7 8177 if (lrelfixoff != 0)
07d6d2b8
AM
8178 {
8179 fprintf (file, _(" long-word relocation fixups:\n"));
8180 evax_bfd_print_relocation_records (file, buf + lrelfixoff, 4);
8181 }
95e34ef7 8182 if (qdotadroff != 0)
07d6d2b8
AM
8183 {
8184 fprintf (file, _(" quad-word .address reference fixups:\n"));
8185 evax_bfd_print_address_fixups (file, buf + qdotadroff);
8186 }
95e34ef7 8187 if (ldotadroff != 0)
07d6d2b8
AM
8188 {
8189 fprintf (file, _(" long-word .address reference fixups:\n"));
8190 evax_bfd_print_address_fixups (file, buf + ldotadroff);
8191 }
95e34ef7 8192 if (codeadroff != 0)
07d6d2b8
AM
8193 {
8194 fprintf (file, _(" Code Address Reference Fixups:\n"));
8195 evax_bfd_print_reference_fixups (file, buf + codeadroff);
8196 }
95e34ef7 8197 if (lpfixoff != 0)
07d6d2b8
AM
8198 {
8199 fprintf (file, _(" Linkage Pairs Reference Fixups:\n"));
8200 evax_bfd_print_reference_fixups (file, buf + lpfixoff);
8201 }
95e34ef7 8202 if (chgprtoff)
07d6d2b8
AM
8203 {
8204 unsigned int count = (unsigned)bfd_getl32 (buf + chgprtoff);
8205 struct vms_eicp *eicp = (struct vms_eicp *)(buf + chgprtoff + 4);
8206 unsigned int j;
8207
8208 fprintf (file, _(" Change Protection (%u entries):\n"), count);
8209 for (j = 0; j < count; j++, eicp++)
8210 {
8211 unsigned int prot = bfd_getl32 (eicp->newprt);
8212 fprintf (file,
695344c0 8213 /* xgettext:c-format */
07d6d2b8
AM
8214 _(" base: 0x%08x %08x, size: 0x%08x, prot: 0x%08x "),
8215 (unsigned)bfd_getl32 (eicp->baseva + 4),
8216 (unsigned)bfd_getl32 (eicp->baseva + 0),
8217 (unsigned)bfd_getl32 (eicp->size),
8218 (unsigned)bfd_getl32 (eicp->newprt));
8219 switch (prot)
8220 {
8221 case PRT__C_NA:
8222 fprintf (file, "NA");
8223 break;
8224 case PRT__C_RESERVED:
8225 fprintf (file, "RES");
8226 break;
8227 case PRT__C_KW:
8228 fprintf (file, "KW");
8229 break;
8230 case PRT__C_KR:
8231 fprintf (file, "KR");
8232 break;
8233 case PRT__C_UW:
8234 fprintf (file, "UW");
8235 break;
8236 case PRT__C_EW:
8237 fprintf (file, "EW");
8238 break;
8239 case PRT__C_ERKW:
8240 fprintf (file, "ERKW");
8241 break;
8242 case PRT__C_ER:
8243 fprintf (file, "ER");
8244 break;
8245 case PRT__C_SW:
8246 fprintf (file, "SW");
8247 break;
8248 case PRT__C_SREW:
8249 fprintf (file, "SREW");
8250 break;
8251 case PRT__C_SRKW:
8252 fprintf (file, "SRKW");
8253 break;
8254 case PRT__C_SR:
8255 fprintf (file, "SR");
8256 break;
8257 case PRT__C_URSW:
8258 fprintf (file, "URSW");
8259 break;
8260 case PRT__C_UREW:
8261 fprintf (file, "UREW");
8262 break;
8263 case PRT__C_URKW:
8264 fprintf (file, "URKW");
8265 break;
8266 case PRT__C_UR:
8267 fprintf (file, "UR");
8268 break;
8269 default:
8270 fputs ("??", file);
8271 break;
8272 }
8273 fputc ('\n', file);
8274 }
8275 }
95e34ef7
TG
8276 free (buf);
8277 }
8278}
8279
8280static bfd_boolean
8281vms_bfd_print_private_bfd_data (bfd *abfd, void *ptr)
8282{
8283 FILE *file = (FILE *)ptr;
8284
8285 if (bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC))
8286 evax_bfd_print_image (abfd, file);
8287 else
8288 {
8289 if (bfd_seek (abfd, 0, SEEK_SET))
07d6d2b8 8290 return FALSE;
95e34ef7
TG
8291 evax_bfd_print_eobj (abfd, file);
8292 }
8293 return TRUE;
8294}
8295\f
8296/* Linking. */
8297
44273c5b 8298/* Slurp ETIR/EDBG/ETBT VMS object records. */
95e34ef7
TG
8299
8300static bfd_boolean
8301alpha_vms_read_sections_content (bfd *abfd, struct bfd_link_info *info)
8302{
8303 asection *cur_section;
8304 file_ptr cur_offset;
8305 asection *dst_section;
8306 file_ptr dst_offset;
8307
8308 if (bfd_seek (abfd, 0, SEEK_SET) != 0)
8309 return FALSE;
8310
95e34ef7
TG
8311 cur_section = NULL;
8312 cur_offset = 0;
8313
8314 dst_section = PRIV (dst_section);
8315 dst_offset = 0;
8316 if (info)
8317 {
8318 if (info->strip == strip_all || info->strip == strip_debugger)
07d6d2b8
AM
8319 {
8320 /* Discard the DST section. */
8321 dst_offset = 0;
8322 dst_section = NULL;
8323 }
95e34ef7 8324 else if (dst_section)
07d6d2b8
AM
8325 {
8326 dst_offset = dst_section->output_offset;
8327 dst_section = dst_section->output_section;
8328 }
95e34ef7
TG
8329 }
8330
8331 while (1)
8332 {
8333 int type;
8334 bfd_boolean res;
8335
8336 type = _bfd_vms_get_object_record (abfd);
8337 if (type < 0)
8338 {
8339 vms_debug2 ((2, "next_record failed\n"));
8340 return FALSE;
8341 }
8342 switch (type)
07d6d2b8
AM
8343 {
8344 case EOBJ__C_ETIR:
8345 PRIV (image_section) = cur_section;
8346 PRIV (image_offset) = cur_offset;
8347 res = _bfd_vms_slurp_etir (abfd, info);
8348 cur_section = PRIV (image_section);
8349 cur_offset = PRIV (image_offset);
8350 break;
8351 case EOBJ__C_EDBG:
8352 case EOBJ__C_ETBT:
8353 if (dst_section == NULL)
8354 continue;
8355 PRIV (image_section) = dst_section;
8356 PRIV (image_offset) = dst_offset;
8357 res = _bfd_vms_slurp_etir (abfd, info);
8358 dst_offset = PRIV (image_offset);
8359 break;
8360 case EOBJ__C_EEOM:
8361 return TRUE;
8362 default:
8363 continue;
8364 }
95e34ef7 8365 if (!res)
07d6d2b8
AM
8366 {
8367 vms_debug2 ((2, "slurp eobj type %d failed\n", type));
8368 return FALSE;
8369 }
95e34ef7
TG
8370 }
8371}
8372
8373static int
8374alpha_vms_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
07d6d2b8 8375 struct bfd_link_info *info ATTRIBUTE_UNUSED)
95e34ef7
TG
8376{
8377 return 0;
8378}
8379
8380/* Add a linkage pair fixup at address SECT + OFFSET to SHLIB. */
8381
96d3b80f 8382static bfd_boolean
95e34ef7
TG
8383alpha_vms_add_fixup_lp (struct bfd_link_info *info, bfd *src, bfd *shlib)
8384{
8385 struct alpha_vms_shlib_el *sl;
8386 asection *sect = PRIV2 (src, image_section);
8387 file_ptr offset = PRIV2 (src, image_offset);
96d3b80f 8388 bfd_vma *p;
95e34ef7
TG
8389
8390 sl = &VEC_EL (alpha_vms_link_hash (info)->shrlibs,
07d6d2b8 8391 struct alpha_vms_shlib_el, PRIV2 (shlib, shr_index));
95e34ef7 8392 sl->has_fixups = TRUE;
96d3b80f
AM
8393 p = VEC_APPEND (sl->lp, bfd_vma);
8394 if (p == NULL)
8395 return FALSE;
8396 *p = sect->output_section->vma + sect->output_offset + offset;
5f101a3d 8397 sect->output_section->flags |= SEC_RELOC;
96d3b80f 8398 return TRUE;
95e34ef7
TG
8399}
8400
5f101a3d
TG
8401/* Add a code address fixup at address SECT + OFFSET to SHLIB. */
8402
96d3b80f 8403static bfd_boolean
95e34ef7
TG
8404alpha_vms_add_fixup_ca (struct bfd_link_info *info, bfd *src, bfd *shlib)
8405{
8406 struct alpha_vms_shlib_el *sl;
8407 asection *sect = PRIV2 (src, image_section);
8408 file_ptr offset = PRIV2 (src, image_offset);
96d3b80f 8409 bfd_vma *p;
95e34ef7
TG
8410
8411 sl = &VEC_EL (alpha_vms_link_hash (info)->shrlibs,
07d6d2b8 8412 struct alpha_vms_shlib_el, PRIV2 (shlib, shr_index));
95e34ef7 8413 sl->has_fixups = TRUE;
96d3b80f
AM
8414 p = VEC_APPEND (sl->ca, bfd_vma);
8415 if (p == NULL)
8416 return FALSE;
8417 *p = sect->output_section->vma + sect->output_offset + offset;
5f101a3d 8418 sect->output_section->flags |= SEC_RELOC;
96d3b80f 8419 return TRUE;
95e34ef7
TG
8420}
8421
5f101a3d
TG
8422/* Add a quad word relocation fixup at address SECT + OFFSET to SHLIB. */
8423
96d3b80f 8424static bfd_boolean
95e34ef7 8425alpha_vms_add_fixup_qr (struct bfd_link_info *info, bfd *src,
07d6d2b8 8426 bfd *shlib, bfd_vma vec)
95e34ef7
TG
8427{
8428 struct alpha_vms_shlib_el *sl;
8429 struct alpha_vms_vma_ref *r;
8430 asection *sect = PRIV2 (src, image_section);
8431 file_ptr offset = PRIV2 (src, image_offset);
8432
8433 sl = &VEC_EL (alpha_vms_link_hash (info)->shrlibs,
07d6d2b8 8434 struct alpha_vms_shlib_el, PRIV2 (shlib, shr_index));
95e34ef7
TG
8435 sl->has_fixups = TRUE;
8436 r = VEC_APPEND (sl->qr, struct alpha_vms_vma_ref);
96d3b80f
AM
8437 if (r == NULL)
8438 return FALSE;
95e34ef7
TG
8439 r->vma = sect->output_section->vma + sect->output_offset + offset;
8440 r->ref = vec;
5f101a3d 8441 sect->output_section->flags |= SEC_RELOC;
96d3b80f 8442 return TRUE;
95e34ef7
TG
8443}
8444
96d3b80f 8445static bfd_boolean
5369db0a 8446alpha_vms_add_fixup_lr (struct bfd_link_info *info ATTRIBUTE_UNUSED,
07d6d2b8
AM
8447 unsigned int shr ATTRIBUTE_UNUSED,
8448 bfd_vma vec ATTRIBUTE_UNUSED)
95e34ef7 8449{
5f101a3d 8450 /* Not yet supported. */
96d3b80f 8451 return FALSE;
95e34ef7
TG
8452}
8453
5369db0a 8454/* Add relocation. FIXME: Not yet emitted. */
95e34ef7 8455
96d3b80f 8456static bfd_boolean
95e34ef7
TG
8457alpha_vms_add_lw_reloc (struct bfd_link_info *info ATTRIBUTE_UNUSED)
8458{
96d3b80f 8459 return FALSE;
95e34ef7
TG
8460}
8461
96d3b80f 8462static bfd_boolean
95e34ef7
TG
8463alpha_vms_add_qw_reloc (struct bfd_link_info *info ATTRIBUTE_UNUSED)
8464{
96d3b80f 8465 return FALSE;
95e34ef7
TG
8466}
8467
8468static struct bfd_hash_entry *
8469alpha_vms_link_hash_newfunc (struct bfd_hash_entry *entry,
07d6d2b8
AM
8470 struct bfd_hash_table *table,
8471 const char *string)
95e34ef7
TG
8472{
8473 struct alpha_vms_link_hash_entry *ret =
8474 (struct alpha_vms_link_hash_entry *) entry;
8475
8476 /* Allocate the structure if it has not already been allocated by a
8477 subclass. */
8478 if (ret == NULL)
8479 ret = ((struct alpha_vms_link_hash_entry *)
8480 bfd_hash_allocate (table,
07d6d2b8 8481 sizeof (struct alpha_vms_link_hash_entry)));
95e34ef7
TG
8482 if (ret == NULL)
8483 return NULL;
8484
8485 /* Call the allocation method of the superclass. */
8486 ret = ((struct alpha_vms_link_hash_entry *)
8487 _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret,
8488 table, string));
8489
8490 ret->sym = NULL;
8491
8492 return (struct bfd_hash_entry *) ret;
8493}
8494
37d2e9c7
AM
8495static void
8496alpha_vms_bfd_link_hash_table_free (bfd *abfd)
8497{
8498 struct alpha_vms_link_hash_table *t;
8499 unsigned i;
8500
8501 t = (struct alpha_vms_link_hash_table *) abfd->link.hash;
8502 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
8503 {
8504 struct alpha_vms_shlib_el *shlib;
8505
8506 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
8507 free (&VEC_EL (shlib->ca, bfd_vma, 0));
8508 free (&VEC_EL (shlib->lp, bfd_vma, 0));
8509 free (&VEC_EL (shlib->qr, struct alpha_vms_vma_ref, 0));
8510 }
8511 free (&VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, 0));
8512
8513 _bfd_generic_link_hash_table_free (abfd);
8514}
8515
95e34ef7
TG
8516/* Create an Alpha/VMS link hash table. */
8517
8518static struct bfd_link_hash_table *
8519alpha_vms_bfd_link_hash_table_create (bfd *abfd)
8520{
8521 struct alpha_vms_link_hash_table *ret;
986f0783 8522 size_t amt = sizeof (struct alpha_vms_link_hash_table);
95e34ef7
TG
8523
8524 ret = (struct alpha_vms_link_hash_table *) bfd_malloc (amt);
8525 if (ret == NULL)
8526 return NULL;
8527 if (!_bfd_link_hash_table_init (&ret->root, abfd,
8528 alpha_vms_link_hash_newfunc,
8529 sizeof (struct alpha_vms_link_hash_entry)))
8530 {
8531 free (ret);
8532 return NULL;
8533 }
8534
8535 VEC_INIT (ret->shrlibs);
8536 ret->fixup = NULL;
37d2e9c7 8537 ret->root.hash_table_free = alpha_vms_bfd_link_hash_table_free;
95e34ef7
TG
8538
8539 return &ret->root;
8540}
8541
8542static bfd_boolean
8543alpha_vms_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
8544{
8545 unsigned int i;
8546
8547 for (i = 0; i < PRIV (gsd_sym_count); i++)
8548 {
8549 struct vms_symbol_entry *e = PRIV (syms)[i];
8550 struct alpha_vms_link_hash_entry *h;
11afaeda 8551 struct bfd_link_hash_entry *h_root;
95e34ef7
TG
8552 asymbol sym;
8553
8554 if (!alpha_vms_convert_symbol (abfd, e, &sym))
07d6d2b8 8555 return FALSE;
95e34ef7
TG
8556
8557 if ((e->flags & EGSY__V_DEF) && abfd->selective_search)
07d6d2b8
AM
8558 {
8559 /* In selective_search mode, only add definition that are
8560 required. */
8561 h = (struct alpha_vms_link_hash_entry *)bfd_link_hash_lookup
8562 (info->hash, sym.name, FALSE, FALSE, FALSE);
8563 if (h == NULL || h->root.type != bfd_link_hash_undefined)
8564 continue;
8565 }
95e34ef7 8566 else
07d6d2b8 8567 h = NULL;
95e34ef7 8568
11afaeda 8569 h_root = (struct bfd_link_hash_entry *) h;
535b785f
AM
8570 if (!_bfd_generic_link_add_one_symbol (info, abfd, sym.name, sym.flags,
8571 sym.section, sym.value, NULL,
8572 FALSE, FALSE, &h_root))
07d6d2b8 8573 return FALSE;
11afaeda 8574 h = (struct alpha_vms_link_hash_entry *) h_root;
95e34ef7
TG
8575
8576 if ((e->flags & EGSY__V_DEF)
07d6d2b8
AM
8577 && h->sym == NULL
8578 && abfd->xvec == info->output_bfd->xvec)
8579 h->sym = e;
95e34ef7
TG
8580 }
8581
8582 if (abfd->flags & DYNAMIC)
8583 {
8584 struct alpha_vms_shlib_el *shlib;
8585
8586 /* We do not want to include any of the sections in a dynamic
07d6d2b8 8587 object in the output file. See comment in elflink.c. */
95e34ef7
TG
8588 bfd_section_list_clear (abfd);
8589
8590 shlib = VEC_APPEND (alpha_vms_link_hash (info)->shrlibs,
07d6d2b8 8591 struct alpha_vms_shlib_el);
96d3b80f
AM
8592 if (shlib == NULL)
8593 return FALSE;
95e34ef7
TG
8594 shlib->abfd = abfd;
8595 VEC_INIT (shlib->ca);
8596 VEC_INIT (shlib->lp);
8597 VEC_INIT (shlib->qr);
8598 PRIV (shr_index) = VEC_COUNT (alpha_vms_link_hash (info)->shrlibs) - 1;
8599 }
8600
8601 return TRUE;
8602}
8603
8604static bfd_boolean
8605alpha_vms_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
8606{
8607 int pass;
8608 struct bfd_link_hash_entry **pundef;
8609 struct bfd_link_hash_entry **next_pundef;
8610
8611 /* We only accept VMS libraries. */
8612 if (info->output_bfd->xvec != abfd->xvec)
8613 {
8614 bfd_set_error (bfd_error_wrong_format);
8615 return FALSE;
8616 }
8617
8618 /* The archive_pass field in the archive itself is used to
8619 initialize PASS, since we may search the same archive multiple
8620 times. */
8621 pass = ++abfd->archive_pass;
8622
8623 /* Look through the list of undefined symbols. */
8624 for (pundef = &info->hash->undefs; *pundef != NULL; pundef = next_pundef)
8625 {
8626 struct bfd_link_hash_entry *h;
8e57e1d1 8627 symindex symidx;
95e34ef7
TG
8628 bfd *element;
8629 bfd *orig_element;
8630
8631 h = *pundef;
8632 next_pundef = &(*pundef)->u.undef.next;
8633
8634 /* When a symbol is defined, it is not necessarily removed from
8635 the list. */
8636 if (h->type != bfd_link_hash_undefined
8637 && h->type != bfd_link_hash_common)
8638 {
8639 /* Remove this entry from the list, for general cleanliness
8640 and because we are going to look through the list again
8641 if we search any more libraries. We can't remove the
8642 entry if it is the tail, because that would lose any
8643 entries we add to the list later on. */
8644 if (*pundef != info->hash->undefs_tail)
07d6d2b8
AM
8645 {
8646 *pundef = *next_pundef;
8647 next_pundef = pundef;
8648 }
95e34ef7
TG
8649 continue;
8650 }
8651
8652 /* Look for this symbol in the archive hash table. */
8e57e1d1
TG
8653 symidx = _bfd_vms_lib_find_symbol (abfd, h->root.string);
8654 if (symidx == BFD_NO_MORE_SYMBOLS)
95e34ef7
TG
8655 {
8656 /* Nothing in this slot. */
8657 continue;
8658 }
8659
8e57e1d1 8660 element = bfd_get_elt_at_index (abfd, symidx);
95e34ef7
TG
8661 if (element == NULL)
8662 return FALSE;
8663
8664 if (element->archive_pass == -1 || element->archive_pass == pass)
07d6d2b8
AM
8665 {
8666 /* Next symbol if this archive is wrong or already handled. */
8667 continue;
8668 }
95e34ef7
TG
8669
8670 if (! bfd_check_format (element, bfd_object))
07d6d2b8
AM
8671 {
8672 element->archive_pass = -1;
8673 return FALSE;
8674 }
95e34ef7
TG
8675
8676 orig_element = element;
8677 if (bfd_is_thin_archive (abfd))
07d6d2b8
AM
8678 {
8679 element = _bfd_vms_lib_get_imagelib_file (element);
8680 if (element == NULL || !bfd_check_format (element, bfd_object))
8681 {
8682 orig_element->archive_pass = -1;
8683 return FALSE;
8684 }
8685 }
95e34ef7
TG
8686
8687 /* Unlike the generic linker, we know that this element provides
8688 a definition for an undefined symbol and we know that we want
8689 to include it. We don't need to check anything. */
0e144ba7
AM
8690 if (!(*info->callbacks
8691 ->add_archive_element) (info, element, h->root.string, &element))
b95a0a31 8692 continue;
0e144ba7 8693 if (!alpha_vms_link_add_object_symbols (element, info))
95e34ef7
TG
8694 return FALSE;
8695
8696 orig_element->archive_pass = pass;
8697 }
8698
8699 return TRUE;
8700}
8701
8702static bfd_boolean
8703alpha_vms_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
8704{
8705 switch (bfd_get_format (abfd))
8706 {
8707 case bfd_object:
8708 vms_debug2 ((2, "vms_link_add_symbols for object %s\n",
07d6d2b8 8709 abfd->filename));
95e34ef7
TG
8710 return alpha_vms_link_add_object_symbols (abfd, info);
8711 break;
8712 case bfd_archive:
8713 vms_debug2 ((2, "vms_link_add_symbols for archive %s\n",
07d6d2b8 8714 abfd->filename));
95e34ef7
TG
8715 return alpha_vms_link_add_archive_symbols (abfd, info);
8716 break;
8717 default:
8718 bfd_set_error (bfd_error_wrong_format);
8719 return FALSE;
8720 }
8721}
8722
8723static bfd_boolean
8724alpha_vms_build_fixups (struct bfd_link_info *info)
8725{
8726 struct alpha_vms_link_hash_table *t = alpha_vms_link_hash (info);
8727 unsigned char *content;
8728 unsigned int i;
8729 unsigned int sz = 0;
8730 unsigned int lp_sz = 0;
8731 unsigned int ca_sz = 0;
8732 unsigned int qr_sz = 0;
8733 unsigned int shrimg_cnt = 0;
79326a5a
TG
8734 unsigned int chgprt_num = 0;
8735 unsigned int chgprt_sz = 0;
95e34ef7
TG
8736 struct vms_eiaf *eiaf;
8737 unsigned int off;
8738 asection *sec;
8739
8740 /* Shared libraries. */
8741 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
8742 {
8743 struct alpha_vms_shlib_el *shlib;
8744
8745 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
8746
8747 if (!shlib->has_fixups)
07d6d2b8 8748 continue;
95e34ef7
TG
8749
8750 shrimg_cnt++;
8751
8752 if (VEC_COUNT (shlib->ca) > 0)
07d6d2b8
AM
8753 {
8754 /* Header + entries. */
8755 ca_sz += 8;
8756 ca_sz += VEC_COUNT (shlib->ca) * 4;
8757 }
95e34ef7 8758 if (VEC_COUNT (shlib->lp) > 0)
07d6d2b8
AM
8759 {
8760 /* Header + entries. */
8761 lp_sz += 8;
8762 lp_sz += VEC_COUNT (shlib->lp) * 4;
8763 }
95e34ef7 8764 if (VEC_COUNT (shlib->qr) > 0)
07d6d2b8
AM
8765 {
8766 /* Header + entries. */
8767 qr_sz += 8;
8768 qr_sz += VEC_COUNT (shlib->qr) * 8;
8769 }
95e34ef7
TG
8770 }
8771 /* Add markers. */
8772 if (ca_sz > 0)
8773 ca_sz += 8;
8774 if (lp_sz > 0)
8775 lp_sz += 8;
8776 if (qr_sz > 0)
8777 qr_sz += 8;
8778
8779 /* Finish now if there is no content. */
8780 if (ca_sz + lp_sz + qr_sz == 0)
8781 return TRUE;
8782
79326a5a
TG
8783 /* Add an eicp entry for the fixup itself. */
8784 chgprt_num = 1;
8785 for (sec = info->output_bfd->sections; sec != NULL; sec = sec->next)
8786 {
8787 /* This isect could be made RO or EXE after relocations are applied. */
8788 if ((sec->flags & SEC_RELOC) != 0
07d6d2b8
AM
8789 && (sec->flags & (SEC_CODE | SEC_READONLY)) != 0)
8790 chgprt_num++;
79326a5a
TG
8791 }
8792 chgprt_sz = 4 + chgprt_num * sizeof (struct vms_eicp);
8793
95e34ef7
TG
8794 /* Allocate section content (round-up size) */
8795 sz = sizeof (struct vms_eiaf) + shrimg_cnt * sizeof (struct vms_shl)
79326a5a 8796 + ca_sz + lp_sz + qr_sz + chgprt_sz;
95e34ef7
TG
8797 sz = (sz + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1);
8798 content = bfd_zalloc (info->output_bfd, sz);
8799 if (content == NULL)
8800 return FALSE;
8801
8802 sec = alpha_vms_link_hash (info)->fixup;
8803 sec->contents = content;
8804 sec->size = sz;
8805
8806 eiaf = (struct vms_eiaf *)content;
8807 off = sizeof (struct vms_eiaf);
8808 bfd_putl32 (0, eiaf->majorid);
8809 bfd_putl32 (0, eiaf->minorid);
8810 bfd_putl32 (0, eiaf->iaflink);
8811 bfd_putl32 (0, eiaf->fixuplnk);
8812 bfd_putl32 (sizeof (struct vms_eiaf), eiaf->size);
8813 bfd_putl32 (0, eiaf->flags);
8814 bfd_putl32 (0, eiaf->qrelfixoff);
8815 bfd_putl32 (0, eiaf->lrelfixoff);
8816 bfd_putl32 (0, eiaf->qdotadroff);
8817 bfd_putl32 (0, eiaf->ldotadroff);
8818 bfd_putl32 (0, eiaf->codeadroff);
8819 bfd_putl32 (0, eiaf->lpfixoff);
8820 bfd_putl32 (0, eiaf->chgprtoff);
8821 bfd_putl32 (shrimg_cnt ? off : 0, eiaf->shlstoff);
8822 bfd_putl32 (shrimg_cnt, eiaf->shrimgcnt);
8823 bfd_putl32 (0, eiaf->shlextra);
8824 bfd_putl32 (0, eiaf->permctx);
8825 bfd_putl32 (0, eiaf->base_va);
8826 bfd_putl32 (0, eiaf->lppsbfixoff);
8827
8828 if (shrimg_cnt)
8829 {
8830 shrimg_cnt = 0;
8831
8832 /* Write shl. */
8833 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
07d6d2b8
AM
8834 {
8835 struct alpha_vms_shlib_el *shlib;
8836 struct vms_shl *shl;
8837
8838 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
8839
8840 if (!shlib->has_fixups)
8841 continue;
8842
8843 /* Renumber shared images. */
8844 PRIV2 (shlib->abfd, shr_index) = shrimg_cnt++;
8845
8846 shl = (struct vms_shl *)(content + off);
8847 bfd_putl32 (0, shl->baseva);
8848 bfd_putl32 (0, shl->shlptr);
8849 bfd_putl32 (0, shl->ident);
8850 bfd_putl32 (0, shl->permctx);
8851 shl->size = sizeof (struct vms_shl);
8852 bfd_putl16 (0, shl->fill_1);
8853 shl->flags = 0;
8854 bfd_putl32 (0, shl->icb);
8855 shl->imgnam[0] = strlen (PRIV2 (shlib->abfd, hdr_data.hdr_t_name));
8856 memcpy (shl->imgnam + 1, PRIV2 (shlib->abfd, hdr_data.hdr_t_name),
8857 shl->imgnam[0]);
8858
8859 off += sizeof (struct vms_shl);
8860 }
95e34ef7
TG
8861
8862 /* CA fixups. */
8863 if (ca_sz != 0)
07d6d2b8
AM
8864 {
8865 bfd_putl32 (off, eiaf->codeadroff);
95e34ef7 8866
07d6d2b8
AM
8867 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
8868 {
8869 struct alpha_vms_shlib_el *shlib;
8870 unsigned int j;
95e34ef7 8871
07d6d2b8 8872 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
95e34ef7 8873
07d6d2b8
AM
8874 if (VEC_COUNT (shlib->ca) == 0)
8875 continue;
95e34ef7 8876
07d6d2b8
AM
8877 bfd_putl32 (VEC_COUNT (shlib->ca), content + off);
8878 bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4);
8879 off += 8;
95e34ef7 8880
07d6d2b8
AM
8881 for (j = 0; j < VEC_COUNT (shlib->ca); j++)
8882 {
8883 bfd_putl32 (VEC_EL (shlib->ca, bfd_vma, j) - t->base_addr,
8884 content + off);
8885 off += 4;
8886 }
8887 }
95e34ef7 8888
07d6d2b8
AM
8889 bfd_putl32 (0, content + off);
8890 bfd_putl32 (0, content + off + 4);
8891 off += 8;
8892 }
95e34ef7
TG
8893
8894 /* LP fixups. */
8895 if (lp_sz != 0)
07d6d2b8
AM
8896 {
8897 bfd_putl32 (off, eiaf->lpfixoff);
95e34ef7 8898
07d6d2b8
AM
8899 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
8900 {
8901 struct alpha_vms_shlib_el *shlib;
8902 unsigned int j;
95e34ef7 8903
07d6d2b8 8904 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
95e34ef7 8905
07d6d2b8
AM
8906 if (VEC_COUNT (shlib->lp) == 0)
8907 continue;
95e34ef7 8908
07d6d2b8
AM
8909 bfd_putl32 (VEC_COUNT (shlib->lp), content + off);
8910 bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4);
8911 off += 8;
95e34ef7 8912
07d6d2b8
AM
8913 for (j = 0; j < VEC_COUNT (shlib->lp); j++)
8914 {
8915 bfd_putl32 (VEC_EL (shlib->lp, bfd_vma, j) - t->base_addr,
8916 content + off);
8917 off += 4;
8918 }
8919 }
95e34ef7 8920
07d6d2b8
AM
8921 bfd_putl32 (0, content + off);
8922 bfd_putl32 (0, content + off + 4);
8923 off += 8;
8924 }
95e34ef7
TG
8925
8926 /* QR fixups. */
8927 if (qr_sz != 0)
07d6d2b8
AM
8928 {
8929 bfd_putl32 (off, eiaf->qdotadroff);
95e34ef7 8930
07d6d2b8
AM
8931 for (i = 0; i < VEC_COUNT (t->shrlibs); i++)
8932 {
8933 struct alpha_vms_shlib_el *shlib;
8934 unsigned int j;
95e34ef7 8935
07d6d2b8 8936 shlib = &VEC_EL (t->shrlibs, struct alpha_vms_shlib_el, i);
95e34ef7 8937
07d6d2b8
AM
8938 if (VEC_COUNT (shlib->qr) == 0)
8939 continue;
95e34ef7 8940
07d6d2b8
AM
8941 bfd_putl32 (VEC_COUNT (shlib->qr), content + off);
8942 bfd_putl32 (PRIV2 (shlib->abfd, shr_index), content + off + 4);
8943 off += 8;
95e34ef7 8944
07d6d2b8
AM
8945 for (j = 0; j < VEC_COUNT (shlib->qr); j++)
8946 {
8947 struct alpha_vms_vma_ref *r;
8948 r = &VEC_EL (shlib->qr, struct alpha_vms_vma_ref, j);
8949 bfd_putl32 (r->vma - t->base_addr, content + off);
8950 bfd_putl32 (r->ref, content + off + 4);
8951 off += 8;
8952 }
8953 }
95e34ef7 8954
07d6d2b8
AM
8955 bfd_putl32 (0, content + off);
8956 bfd_putl32 (0, content + off + 4);
8957 off += 8;
8958 }
95e34ef7
TG
8959 }
8960
79326a5a
TG
8961 /* Write the change protection table. */
8962 bfd_putl32 (off, eiaf->chgprtoff);
8963 bfd_putl32 (chgprt_num, content + off);
8964 off += 4;
8965
8966 for (sec = info->output_bfd->sections; sec != NULL; sec = sec->next)
8967 {
8968 struct vms_eicp *eicp;
8969 unsigned int prot;
8970
8971 if ((sec->flags & SEC_LINKER_CREATED) != 0 &&
07d6d2b8
AM
8972 strcmp (sec->name, "$FIXUP$") == 0)
8973 prot = PRT__C_UREW;
79326a5a 8974 else if ((sec->flags & SEC_RELOC) != 0
07d6d2b8
AM
8975 && (sec->flags & (SEC_CODE | SEC_READONLY)) != 0)
8976 prot = PRT__C_UR;
79326a5a 8977 else
07d6d2b8 8978 continue;
79326a5a
TG
8979
8980 eicp = (struct vms_eicp *)(content + off);
8981 bfd_putl64 (sec->vma - t->base_addr, eicp->baseva);
8982 bfd_putl32 ((sec->size + VMS_BLOCK_SIZE - 1) & ~(VMS_BLOCK_SIZE - 1),
07d6d2b8 8983 eicp->size);
79326a5a
TG
8984 bfd_putl32 (prot, eicp->newprt);
8985 off += sizeof (struct vms_eicp);
8986 }
8987
95e34ef7
TG
8988 return TRUE;
8989}
8990
7686d77d 8991/* Called by bfd_hash_traverse to fill the symbol table.
f9eeb9c9
TG
8992 Return FALSE in case of failure. */
8993
8994static bfd_boolean
7686d77d 8995alpha_vms_link_output_symbol (struct bfd_hash_entry *bh, void *infov)
f9eeb9c9 8996{
7686d77d 8997 struct bfd_link_hash_entry *hc = (struct bfd_link_hash_entry *) bh;
f9eeb9c9 8998 struct bfd_link_info *info = (struct bfd_link_info *)infov;
7686d77d 8999 struct alpha_vms_link_hash_entry *h;
f9eeb9c9
TG
9000 struct vms_symbol_entry *sym;
9001
7686d77d
AM
9002 if (hc->type == bfd_link_hash_warning)
9003 {
9004 hc = hc->u.i.link;
9005 if (hc->type == bfd_link_hash_new)
9006 return TRUE;
9007 }
9008 h = (struct alpha_vms_link_hash_entry *) hc;
9009
f9eeb9c9
TG
9010 switch (h->root.type)
9011 {
f9eeb9c9 9012 case bfd_link_hash_undefined:
8185f55c
TG
9013 return TRUE;
9014 case bfd_link_hash_new:
7686d77d 9015 case bfd_link_hash_warning:
f9eeb9c9
TG
9016 abort ();
9017 case bfd_link_hash_undefweak:
9018 return TRUE;
9019 case bfd_link_hash_defined:
9020 case bfd_link_hash_defweak:
9021 {
07d6d2b8 9022 asection *sec = h->root.u.def.section;
f9eeb9c9 9023
07d6d2b8
AM
9024 /* FIXME: this is certainly a symbol from a dynamic library. */
9025 if (bfd_is_abs_section (sec))
9026 return TRUE;
f9eeb9c9 9027
07d6d2b8
AM
9028 if (sec->owner->flags & DYNAMIC)
9029 return TRUE;
f9eeb9c9
TG
9030 }
9031 break;
9032 case bfd_link_hash_common:
9033 break;
9034 case bfd_link_hash_indirect:
f9eeb9c9
TG
9035 return TRUE;
9036 }
9037
9038 /* Do not write not kept symbols. */
9039 if (info->strip == strip_some
9040 && bfd_hash_lookup (info->keep_hash, h->root.root.string,
07d6d2b8 9041 FALSE, FALSE) != NULL)
f9eeb9c9
TG
9042 return TRUE;
9043
9044 if (h->sym == NULL)
9045 {
9046 /* This symbol doesn't come from a VMS object. So we suppose it is
07d6d2b8 9047 a data. */
f9eeb9c9
TG
9048 int len = strlen (h->root.root.string);
9049
9050 sym = (struct vms_symbol_entry *)bfd_zalloc (info->output_bfd,
07d6d2b8 9051 sizeof (*sym) + len);
f9eeb9c9 9052 if (sym == NULL)
07d6d2b8 9053 abort ();
f9eeb9c9
TG
9054 sym->namelen = len;
9055 memcpy (sym->name, h->root.root.string, len);
9056 sym->name[len] = 0;
9057 sym->owner = info->output_bfd;
9058
9059 sym->typ = EGSD__C_SYMG;
9060 sym->data_type = 0;
9061 sym->flags = EGSY__V_DEF | EGSY__V_REL;
9062 sym->symbol_vector = h->root.u.def.value;
9063 sym->section = h->root.u.def.section;
9064 sym->value = h->root.u.def.value;
9065 }
9066 else
9067 sym = h->sym;
9068
9069 if (!add_symbol_entry (info->output_bfd, sym))
9070 return FALSE;
9071
9072 return TRUE;
9073}
9074
95e34ef7
TG
9075static bfd_boolean
9076alpha_vms_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
9077{
9078 asection *o;
9079 struct bfd_link_order *p;
9080 bfd *sub;
9081 asection *fixupsec;
9082 bfd_vma base_addr;
9083 bfd_vma last_addr;
44273c5b 9084 asection *dst;
fa23f0f4 9085 asection *dmt;
95e34ef7 9086
0e1862bb 9087 if (bfd_link_relocatable (info))
79326a5a
TG
9088 {
9089 /* FIXME: we do not yet support relocatable link. It is not obvious
07d6d2b8 9090 how to do it for debug infos. */
79326a5a
TG
9091 (*info->callbacks->einfo)(_("%P: relocatable link is not supported\n"));
9092 return FALSE;
9093 }
9094
ed48ec2e
AM
9095 abfd->outsymbols = NULL;
9096 abfd->symcount = 0;
95e34ef7
TG
9097
9098 /* Mark all sections which will be included in the output file. */
9099 for (o = abfd->sections; o != NULL; o = o->next)
9100 for (p = o->map_head.link_order; p != NULL; p = p->next)
9101 if (p->type == bfd_indirect_link_order)
9102 p->u.indirect.section->linker_mark = TRUE;
9103
9104#if 0
9105 /* Handle all the link order information for the sections. */
9106 for (o = abfd->sections; o != NULL; o = o->next)
9107 {
9108 printf ("For section %s (at 0x%08x, flags=0x%08x):\n",
07d6d2b8 9109 o->name, (unsigned)o->vma, (unsigned)o->flags);
95e34ef7
TG
9110
9111 for (p = o->map_head.link_order; p != NULL; p = p->next)
9112 {
07d6d2b8
AM
9113 printf (" at 0x%08x - 0x%08x: ",
9114 (unsigned)p->offset, (unsigned)(p->offset + p->size - 1));
95e34ef7
TG
9115 switch (p->type)
9116 {
9117 case bfd_section_reloc_link_order:
9118 case bfd_symbol_reloc_link_order:
07d6d2b8 9119 printf (" section/symbol reloc\n");
95e34ef7
TG
9120 break;
9121 case bfd_indirect_link_order:
07d6d2b8
AM
9122 printf (" section %s of %s\n",
9123 p->u.indirect.section->name,
9124 p->u.indirect.section->owner->filename);
9125 break;
9126 case bfd_data_link_order:
9127 printf (" explicit data\n");
95e34ef7 9128 break;
95e34ef7 9129 default:
07d6d2b8 9130 printf (" *unknown* type %u\n", p->type);
95e34ef7
TG
9131 break;
9132 }
9133 }
9134 }
9135#endif
9136
f9eeb9c9
TG
9137 /* Generate the symbol table. */
9138 BFD_ASSERT (PRIV (syms) == NULL);
9139 if (info->strip != strip_all)
7686d77d 9140 bfd_hash_traverse (&info->hash->table, alpha_vms_link_output_symbol, info);
f9eeb9c9 9141
44273c5b 9142 /* Find the entry point. */
95e34ef7
TG
9143 if (bfd_get_start_address (abfd) == 0)
9144 {
9145 bfd *startbfd = NULL;
9146
c72f2fb2 9147 for (sub = info->input_bfds; sub != NULL; sub = sub->link.next)
07d6d2b8
AM
9148 {
9149 /* Consider only VMS object files. */
9150 if (sub->xvec != abfd->xvec)
9151 continue;
9152
9153 if (!PRIV2 (sub, eom_data).eom_has_transfer)
9154 continue;
9155 if ((PRIV2 (sub, eom_data).eom_b_tfrflg & EEOM__M_WKTFR) && startbfd)
9156 continue;
9157 if (startbfd != NULL
9158 && !(PRIV2 (sub, eom_data).eom_b_tfrflg & EEOM__M_WKTFR))
9159 {
9160 (*info->callbacks->einfo)
695344c0 9161 /* xgettext:c-format */
871b3ab2 9162 (_("%P: multiple entry points: in modules %pB and %pB\n"),
07d6d2b8
AM
9163 startbfd, sub);
9164 continue;
9165 }
9166 startbfd = sub;
9167 }
95e34ef7
TG
9168
9169 if (startbfd)
07d6d2b8
AM
9170 {
9171 unsigned int ps_idx = PRIV2 (startbfd, eom_data).eom_l_psindx;
9172 bfd_vma tfradr = PRIV2 (startbfd, eom_data).eom_l_tfradr;
9173 asection *sec;
95e34ef7 9174
07d6d2b8 9175 sec = PRIV2 (startbfd, sections)[ps_idx];
95e34ef7 9176
07d6d2b8
AM
9177 bfd_set_start_address
9178 (abfd, sec->output_section->vma + sec->output_offset + tfradr);
9179 }
95e34ef7
TG
9180 }
9181
46d00b8a
TG
9182 /* Set transfer addresses. */
9183 {
9184 int i;
9185 struct bfd_link_hash_entry *h;
9186
9187 i = 0;
d0ef7741 9188 PRIV (transfer_address[i++]) = 0xffffffff00000340ULL; /* SYS$IMGACT */
46d00b8a
TG
9189 h = bfd_link_hash_lookup (info->hash, "LIB$INITIALIZE", FALSE, FALSE, TRUE);
9190 if (h != NULL && h->type == bfd_link_hash_defined)
9191 PRIV (transfer_address[i++]) =
07d6d2b8 9192 alpha_vms_get_sym_value (h->u.def.section, h->u.def.value);
46d00b8a
TG
9193 PRIV (transfer_address[i++]) = bfd_get_start_address (abfd);
9194 while (i < 4)
9195 PRIV (transfer_address[i++]) = 0;
9196 }
9197
79326a5a
TG
9198 /* Allocate contents.
9199 Also compute the virtual base address. */
95e34ef7
TG
9200 base_addr = (bfd_vma)-1;
9201 last_addr = 0;
9202 for (o = abfd->sections; o != NULL; o = o->next)
9203 {
9204 if (o->flags & SEC_HAS_CONTENTS)
07d6d2b8
AM
9205 {
9206 o->contents = bfd_alloc (abfd, o->size);
9207 if (o->contents == NULL)
9208 return FALSE;
9209 }
95e34ef7 9210 if (o->flags & SEC_LOAD)
07d6d2b8
AM
9211 {
9212 if (o->vma < base_addr)
9213 base_addr = o->vma;
9214 if (o->vma + o->size > last_addr)
9215 last_addr = o->vma + o->size;
9216 }
79326a5a 9217 /* Clear the RELOC flags. Currently we don't support incremental
07d6d2b8 9218 linking. We use the RELOC flag for computing the eicp entries. */
79326a5a 9219 o->flags &= ~SEC_RELOC;
95e34ef7
TG
9220 }
9221
44273c5b 9222 /* Create the fixup section. */
95e34ef7
TG
9223 fixupsec = bfd_make_section_anyway_with_flags
9224 (info->output_bfd, "$FIXUP$",
9225 SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_LINKER_CREATED);
9226 if (fixupsec == NULL)
9227 return FALSE;
9228 last_addr = (last_addr + 0xffff) & ~0xffff;
9229 fixupsec->vma = last_addr;
9230
9231 alpha_vms_link_hash (info)->fixup = fixupsec;
9232 alpha_vms_link_hash (info)->base_addr = base_addr;
9233
fa23f0f4 9234 /* Create the DMT section, if necessary. */
f9eeb9c9
TG
9235 BFD_ASSERT (PRIV (dst_section) == NULL);
9236 dst = bfd_get_section_by_name (abfd, "$DST$");
fa23f0f4
TG
9237 if (dst != NULL && dst->size == 0)
9238 dst = NULL;
9239 if (dst != NULL)
9240 {
f9eeb9c9 9241 PRIV (dst_section) = dst;
fa23f0f4 9242 dmt = bfd_make_section_anyway_with_flags
07d6d2b8
AM
9243 (info->output_bfd, "$DMT$",
9244 SEC_DEBUGGING | SEC_HAS_CONTENTS | SEC_LINKER_CREATED);
fa23f0f4 9245 if (dmt == NULL)
07d6d2b8 9246 return FALSE;
fa23f0f4
TG
9247 }
9248 else
9249 dmt = NULL;
9250
95e34ef7 9251 /* Read all sections from the inputs. */
c72f2fb2 9252 for (sub = info->input_bfds; sub != NULL; sub = sub->link.next)
95e34ef7
TG
9253 {
9254 if (sub->flags & DYNAMIC)
07d6d2b8
AM
9255 {
9256 alpha_vms_create_eisd_for_shared (abfd, sub);
9257 continue;
9258 }
95e34ef7
TG
9259
9260 if (!alpha_vms_read_sections_content (sub, info))
07d6d2b8 9261 return FALSE;
95e34ef7
TG
9262 }
9263
fa23f0f4
TG
9264 /* Handle all the link order information for the sections.
9265 Note: past this point, it is not possible to create new sections. */
95e34ef7
TG
9266 for (o = abfd->sections; o != NULL; o = o->next)
9267 {
9268 for (p = o->map_head.link_order; p != NULL; p = p->next)
9269 {
9270 switch (p->type)
9271 {
9272 case bfd_section_reloc_link_order:
9273 case bfd_symbol_reloc_link_order:
07d6d2b8
AM
9274 abort ();
9275 return FALSE;
95e34ef7 9276 case bfd_indirect_link_order:
07d6d2b8 9277 /* Already done. */
95e34ef7
TG
9278 break;
9279 default:
9280 if (! _bfd_default_link_order (abfd, info, o, p))
9281 return FALSE;
9282 break;
9283 }
9284 }
9285 }
9286
9287 /* Compute fixups. */
9288 if (!alpha_vms_build_fixups (info))
9289 return FALSE;
9290
44273c5b 9291 /* Compute the DMT. */
fa23f0f4 9292 if (dmt != NULL)
44273c5b 9293 {
44273c5b
TG
9294 int pass;
9295 unsigned char *contents = NULL;
9296
44273c5b
TG
9297 /* In pass 1, compute the size. In pass 2, write the DMT contents. */
9298 for (pass = 0; pass < 2; pass++)
07d6d2b8
AM
9299 {
9300 unsigned int off = 0;
9301
9302 /* For each object file (ie for each module). */
9303 for (sub = info->input_bfds; sub != NULL; sub = sub->link.next)
9304 {
9305 asection *sub_dst;
9306 struct vms_dmt_header *dmth = NULL;
9307 unsigned int psect_count;
9308
9309 /* Skip this module if it has no DST. */
9310 sub_dst = PRIV2 (sub, dst_section);
9311 if (sub_dst == NULL || sub_dst->size == 0)
9312 continue;
9313
9314 if (pass == 1)
9315 {
9316 /* Write the header. */
9317 dmth = (struct vms_dmt_header *)(contents + off);
9318 bfd_putl32 (sub_dst->output_offset, dmth->modbeg);
9319 bfd_putl32 (sub_dst->size, dmth->size);
9320 }
9321
9322 off += sizeof (struct vms_dmt_header);
9323 psect_count = 0;
9324
9325 /* For each section (ie for each psect). */
9326 for (o = sub->sections; o != NULL; o = o->next)
9327 {
9328 /* Only consider interesting sections. */
9329 if (!(o->flags & SEC_ALLOC))
9330 continue;
9331 if (o->flags & SEC_LINKER_CREATED)
9332 continue;
9333
9334 if (pass == 1)
9335 {
9336 /* Write an entry. */
9337 struct vms_dmt_psect *dmtp;
9338
9339 dmtp = (struct vms_dmt_psect *)(contents + off);
9340 bfd_putl32 (o->output_offset + o->output_section->vma,
9341 dmtp->start);
9342 bfd_putl32 (o->size, dmtp->length);
9343 psect_count++;
9344 }
9345 off += sizeof (struct vms_dmt_psect);
9346 }
9347 if (pass == 1)
9348 bfd_putl32 (psect_count, dmth->psect_count);
9349 }
9350
9351 if (pass == 0)
9352 {
9353 contents = bfd_zalloc (info->output_bfd, off);
9354 if (contents == NULL)
9355 return FALSE;
9356 dmt->contents = contents;
9357 dmt->size = off;
9358 }
9359 else
9360 {
9361 BFD_ASSERT (off == dmt->size);
9362 }
9363 }
44273c5b
TG
9364 }
9365
95e34ef7
TG
9366 return TRUE;
9367}
9368
9369/* Read the contents of a section.
9370 buf points to a buffer of buf_size bytes to be filled with
9371 section data (starting at offset into section) */
9372
9373static bfd_boolean
9374alpha_vms_get_section_contents (bfd *abfd, asection *section,
07d6d2b8
AM
9375 void *buf, file_ptr offset,
9376 bfd_size_type count)
95e34ef7
TG
9377{
9378 asection *sec;
9379
9380 /* Image are easy. */
9381 if (bfd_get_file_flags (abfd) & (EXEC_P | DYNAMIC))
9382 return _bfd_generic_get_section_contents (abfd, section,
07d6d2b8 9383 buf, offset, count);
95e34ef7
TG
9384
9385 /* Safety check. */
9386 if (offset + count < count
9387 || offset + count > section->size)
9388 {
9389 bfd_set_error (bfd_error_invalid_operation);
9390 return FALSE;
9391 }
9392
8185f55c
TG
9393 /* If the section is already in memory, just copy it. */
9394 if (section->flags & SEC_IN_MEMORY)
9395 {
9396 BFD_ASSERT (section->contents != NULL);
9397 memcpy (buf, section->contents + offset, count);
9398 return TRUE;
9399 }
9400 if (section->size == 0)
9401 return TRUE;
95e34ef7 9402
8185f55c 9403 /* Alloc in memory and read ETIRs. */
95e34ef7
TG
9404 for (sec = abfd->sections; sec; sec = sec->next)
9405 {
9406 BFD_ASSERT (sec->contents == NULL);
9407
9408 if (sec->size != 0 && (sec->flags & SEC_HAS_CONTENTS))
07d6d2b8
AM
9409 {
9410 sec->contents = bfd_alloc (abfd, sec->size);
9411 if (sec->contents == NULL)
9412 return FALSE;
9413 }
95e34ef7
TG
9414 }
9415 if (!alpha_vms_read_sections_content (abfd, NULL))
9416 return FALSE;
9417 for (sec = abfd->sections; sec; sec = sec->next)
8185f55c
TG
9418 if (sec->contents)
9419 sec->flags |= SEC_IN_MEMORY;
95e34ef7
TG
9420 memcpy (buf, section->contents + offset, count);
9421 return TRUE;
9422}
9423
9424
9425/* Set the format of a file being written. */
9426
9427static bfd_boolean
9428alpha_vms_mkobject (bfd * abfd)
9429{
9430 const bfd_arch_info_type *arch;
9431
9432 vms_debug2 ((1, "alpha_vms_mkobject (%p)\n", abfd));
9433
9434 if (!vms_initialize (abfd))
9435 return FALSE;
9436
9437 PRIV (recwr.buf) = bfd_alloc (abfd, MAX_OUTREC_SIZE);
9438 if (PRIV (recwr.buf) == NULL)
9439 return FALSE;
9440
9441 arch = bfd_scan_arch ("alpha");
9442
9443 if (arch == 0)
9444 {
9445 bfd_set_error (bfd_error_wrong_format);
9446 return FALSE;
9447 }
9448
9449 abfd->arch_info = arch;
9450 return TRUE;
9451}
9452
9453
9454/* 4.1, generic. */
9455
9456/* Called when the BFD is being closed to do any necessary cleanup. */
9457
9458static bfd_boolean
9459vms_close_and_cleanup (bfd * abfd)
9460{
9461 vms_debug2 ((1, "vms_close_and_cleanup (%p)\n", abfd));
9462
9463 if (abfd == NULL || abfd->tdata.any == NULL)
9464 return TRUE;
9465
37d2e9c7 9466 if (abfd->format == bfd_object)
95e34ef7 9467 {
a7ac9aa5 9468 alpha_vms_free_private (abfd);
95e34ef7
TG
9469
9470#ifdef VMS
37d2e9c7
AM
9471 if (abfd->direction == write_direction)
9472 {
9473 /* Last step on VMS is to convert the file to variable record length
9474 format. */
9475 if (!bfd_cache_close (abfd))
9476 return FALSE;
9477 if (!_bfd_vms_convert_to_var_unix_filename (abfd->filename))
9478 return FALSE;
9479 }
95e34ef7 9480#endif
37d2e9c7 9481 }
95e34ef7 9482
37d2e9c7 9483 return _bfd_generic_close_and_cleanup (abfd);
95e34ef7
TG
9484}
9485
9486/* Called when a new section is created. */
9487
9488static bfd_boolean
9489vms_new_section_hook (bfd * abfd, asection *section)
9490{
986f0783 9491 size_t amt;
95e34ef7 9492
d3435ae8 9493 vms_debug2 ((1, "vms_new_section_hook (%p, [%u]%s)\n",
07d6d2b8 9494 abfd, section->index, section->name));
95e34ef7 9495
fd361982 9496 if (!bfd_set_section_alignment (section, 0))
a253d456 9497 return FALSE;
95e34ef7 9498
d3435ae8 9499 vms_debug2 ((7, "%u: %s\n", section->index, section->name));
95e34ef7
TG
9500
9501 amt = sizeof (struct vms_section_data_struct);
8185f55c 9502 section->used_by_bfd = bfd_zalloc (abfd, amt);
95e34ef7
TG
9503 if (section->used_by_bfd == NULL)
9504 return FALSE;
9505
95e34ef7
TG
9506 /* Create the section symbol. */
9507 return _bfd_generic_new_section_hook (abfd, section);
9508}
9509
9510/* Part 4.5, symbols. */
9511
9512/* Print symbol to file according to how. how is one of
9513 bfd_print_symbol_name just print the name
9514 bfd_print_symbol_more print more (???)
9515 bfd_print_symbol_all print all we know, which is not much right now :-). */
9516
9517static void
9518vms_print_symbol (bfd * abfd,
9519 void * file,
9520 asymbol *symbol,
9521 bfd_print_symbol_type how)
9522{
9523 vms_debug2 ((1, "vms_print_symbol (%p, %p, %p, %d)\n",
07d6d2b8 9524 abfd, file, symbol, how));
95e34ef7
TG
9525
9526 switch (how)
9527 {
9528 case bfd_print_symbol_name:
9529 case bfd_print_symbol_more:
9530 fprintf ((FILE *)file," %s", symbol->name);
9531 break;
9532
9533 case bfd_print_symbol_all:
9534 {
9535 const char *section_name = symbol->section->name;
9536
9537 bfd_print_symbol_vandf (abfd, file, symbol);
9538
9539 fprintf ((FILE *) file," %-8s %s", section_name, symbol->name);
07d6d2b8 9540 }
95e34ef7
TG
9541 break;
9542 }
9543}
9544
9545/* Return information about symbol in ret.
9546
9547 fill type, value and name
9548 type:
9549 A absolute
9550 B bss segment symbol
9551 C common symbol
9552 D data segment symbol
9553 f filename
9554 t a static function symbol
9555 T text segment symbol
9556 U undefined
9557 - debug. */
9558
9559static void
9560vms_get_symbol_info (bfd * abfd ATTRIBUTE_UNUSED,
9561 asymbol *symbol,
9562 symbol_info *ret)
9563{
9564 asection *sec;
9565
9566 vms_debug2 ((1, "vms_get_symbol_info (%p, %p, %p)\n", abfd, symbol, ret));
9567
9568 sec = symbol->section;
9569
9570 if (ret == NULL)
9571 return;
9572
a928f1d7 9573 if (sec == NULL)
95e34ef7
TG
9574 ret->type = 'U';
9575 else if (bfd_is_com_section (sec))
9576 ret->type = 'C';
9577 else if (bfd_is_abs_section (sec))
9578 ret->type = 'A';
9579 else if (bfd_is_und_section (sec))
9580 ret->type = 'U';
9581 else if (bfd_is_ind_section (sec))
9582 ret->type = 'I';
c068d5be 9583 else if ((symbol->flags & BSF_FUNCTION)
fd361982 9584 || (bfd_section_flags (sec) & SEC_CODE))
95e34ef7 9585 ret->type = 'T';
fd361982 9586 else if (bfd_section_flags (sec) & SEC_DATA)
95e34ef7 9587 ret->type = 'D';
fd361982 9588 else if (bfd_section_flags (sec) & SEC_ALLOC)
95e34ef7
TG
9589 ret->type = 'B';
9590 else
5369db0a 9591 ret->type = '?';
95e34ef7
TG
9592
9593 if (ret->type != 'U')
9594 ret->value = symbol->value + symbol->section->vma;
9595 else
9596 ret->value = 0;
9597 ret->name = symbol->name;
9598}
9599
9600/* Return TRUE if the given symbol sym in the BFD abfd is
9601 a compiler generated local label, else return FALSE. */
9602
9603static bfd_boolean
9604vms_bfd_is_local_label_name (bfd * abfd ATTRIBUTE_UNUSED,
9605 const char *name)
9606{
95e34ef7
TG
9607 return name[0] == '$';
9608}
9609\f
9610/* Part 4.7, writing an object file. */
9611
9612/* Sets the contents of the section section in BFD abfd to the data starting
9613 in memory at LOCATION. The data is written to the output section starting
9614 at offset offset for count bytes.
9615
9616 Normally TRUE is returned, else FALSE. Possible error returns are:
9617 o bfd_error_no_contents - The output section does not have the
9618 SEC_HAS_CONTENTS attribute, so nothing can be written to it.
9619 o and some more too */
9620
9621static bfd_boolean
9622_bfd_vms_set_section_contents (bfd * abfd,
07d6d2b8
AM
9623 asection *section,
9624 const void * location,
9625 file_ptr offset,
9626 bfd_size_type count)
95e34ef7
TG
9627{
9628 if (section->contents == NULL)
9629 {
9630 section->contents = bfd_alloc (abfd, section->size);
9631 if (section->contents == NULL)
07d6d2b8 9632 return FALSE;
95e34ef7
TG
9633
9634 memcpy (section->contents + offset, location, (size_t) count);
9635 }
9636
9637 return TRUE;
9638}
9639
9640/* Set the architecture and machine type in BFD abfd to arch and mach.
9641 Find the correct pointer to a structure and insert it into the arch_info
9642 pointer. */
9643
9644static bfd_boolean
9645alpha_vms_set_arch_mach (bfd *abfd,
07d6d2b8 9646 enum bfd_architecture arch, unsigned long mach)
95e34ef7
TG
9647{
9648 if (arch != bfd_arch_alpha
9649 && arch != bfd_arch_unknown)
9650 return FALSE;
9651
9652 return bfd_default_set_arch_mach (abfd, arch, mach);
9653}
9654
9655/* Set section VMS flags. Clear NO_FLAGS and set FLAGS. */
9656
9657void
9658bfd_vms_set_section_flags (bfd *abfd ATTRIBUTE_UNUSED,
9659 asection *sec, flagword no_flags, flagword flags)
9660{
9661 vms_section_data (sec)->no_flags = no_flags;
9662 vms_section_data (sec)->flags = flags;
9663}
9664
9665struct vms_private_data_struct *
9666bfd_vms_get_data (bfd *abfd)
9667{
9668 return (struct vms_private_data_struct *)abfd->tdata.any;
9669}
9670
d00dd7dc 9671#define vms_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false
07d6d2b8 9672#define vms_bfd_link_just_syms _bfd_generic_link_just_syms
95e34ef7
TG
9673#define vms_bfd_copy_link_hash_symbol_type \
9674 _bfd_generic_copy_link_hash_symbol_type
07d6d2b8 9675#define vms_bfd_is_group_section bfd_generic_is_group_section
cb7f4b29 9676#define vms_bfd_group_name bfd_generic_group_name
07d6d2b8
AM
9677#define vms_bfd_discard_group bfd_generic_discard_group
9678#define vms_section_already_linked _bfd_generic_section_already_linked
9679#define vms_bfd_define_common_symbol bfd_generic_define_common_symbol
34a87bb0 9680#define vms_bfd_link_hide_symbol _bfd_generic_link_hide_symbol
68d20676 9681#define vms_bfd_define_start_stop bfd_generic_define_start_stop
95e34ef7
TG
9682#define vms_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
9683
9684#define vms_bfd_copy_private_bfd_data _bfd_generic_bfd_copy_private_bfd_data
9685#define vms_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
9686#define vms_bfd_copy_private_section_data _bfd_generic_bfd_copy_private_section_data
9687#define vms_bfd_copy_private_symbol_data _bfd_generic_bfd_copy_private_symbol_data
07d6d2b8
AM
9688#define vms_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
9689#define vms_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
95e34ef7
TG
9690
9691/* Symbols table. */
07d6d2b8 9692#define alpha_vms_make_empty_symbol _bfd_generic_make_empty_symbol
d00dd7dc 9693#define alpha_vms_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false
07d6d2b8
AM
9694#define alpha_vms_print_symbol vms_print_symbol
9695#define alpha_vms_get_symbol_info vms_get_symbol_info
60bb06bc
L
9696#define alpha_vms_get_symbol_version_string \
9697 _bfd_nosymbols_get_symbol_version_string
9698
07d6d2b8
AM
9699#define alpha_vms_read_minisymbols _bfd_generic_read_minisymbols
9700#define alpha_vms_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
9701#define alpha_vms_get_lineno _bfd_nosymbols_get_lineno
9702#define alpha_vms_find_inliner_info _bfd_nosymbols_find_inliner_info
9703#define alpha_vms_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
9704#define alpha_vms_find_nearest_line _bfd_vms_find_nearest_line
9705#define alpha_vms_find_line _bfd_nosymbols_find_line
95e34ef7
TG
9706#define alpha_vms_bfd_is_local_label_name vms_bfd_is_local_label_name
9707
9708/* Generic table. */
9709#define alpha_vms_close_and_cleanup vms_close_and_cleanup
9710#define alpha_vms_bfd_free_cached_info vms_bfd_free_cached_info
9711#define alpha_vms_new_section_hook vms_new_section_hook
9712#define alpha_vms_set_section_contents _bfd_vms_set_section_contents
9713#define alpha_vms_get_section_contents_in_window _bfd_generic_get_section_contents_in_window
9714
9715#define alpha_vms_bfd_get_relocated_section_contents \
9716 bfd_generic_get_relocated_section_contents
9717
9718#define alpha_vms_bfd_relax_section bfd_generic_relax_section
9719#define alpha_vms_bfd_gc_sections bfd_generic_gc_sections
ae17ab41 9720#define alpha_vms_bfd_lookup_section_flags bfd_generic_lookup_section_flags
95e34ef7
TG
9721#define alpha_vms_bfd_merge_sections bfd_generic_merge_sections
9722#define alpha_vms_bfd_is_group_section bfd_generic_is_group_section
cb7f4b29 9723#define alpha_vms_bfd_group_name bfd_generic_group_name
95e34ef7
TG
9724#define alpha_vms_bfd_discard_group bfd_generic_discard_group
9725#define alpha_vms_section_already_linked \
9726 _bfd_generic_section_already_linked
9727
9728#define alpha_vms_bfd_define_common_symbol bfd_generic_define_common_symbol
34a87bb0 9729#define alpha_vms_bfd_link_hide_symbol _bfd_generic_link_hide_symbol
7dba9362 9730#define alpha_vms_bfd_define_start_stop bfd_generic_define_start_stop
95e34ef7
TG
9731#define alpha_vms_bfd_link_just_syms _bfd_generic_link_just_syms
9732#define alpha_vms_bfd_copy_link_hash_symbol_type \
9733 _bfd_generic_copy_link_hash_symbol_type
9734
9735#define alpha_vms_bfd_link_split_section _bfd_generic_link_split_section
9736
9737#define alpha_vms_get_dynamic_symtab_upper_bound \
9738 _bfd_nodynamic_get_dynamic_symtab_upper_bound
9739#define alpha_vms_canonicalize_dynamic_symtab \
9740 _bfd_nodynamic_canonicalize_dynamic_symtab
9741#define alpha_vms_get_dynamic_reloc_upper_bound \
9742 _bfd_nodynamic_get_dynamic_reloc_upper_bound
9743#define alpha_vms_canonicalize_dynamic_reloc \
9744 _bfd_nodynamic_canonicalize_dynamic_reloc
07d6d2b8 9745#define alpha_vms_bfd_link_check_relocs _bfd_generic_link_check_relocs
95e34ef7 9746
6d00b590 9747const bfd_target alpha_vms_vec =
95e34ef7
TG
9748{
9749 "vms-alpha", /* Name. */
9750 bfd_target_evax_flavour,
9751 BFD_ENDIAN_LITTLE, /* Data byte order is little. */
9752 BFD_ENDIAN_LITTLE, /* Header byte order is little. */
9753
9754 (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS
9755 | WP_TEXT | D_PAGED), /* Object flags. */
9756 (SEC_ALLOC | SEC_LOAD | SEC_RELOC
9757 | SEC_READONLY | SEC_CODE | SEC_DATA
9758 | SEC_HAS_CONTENTS | SEC_IN_MEMORY), /* Sect flags. */
9759 0, /* symbol_leading_char. */
9760 ' ', /* ar_pad_char. */
9761 15, /* ar_max_namelen. */
0aabe54e 9762 0, /* match priority. */
95e34ef7
TG
9763 bfd_getl64, bfd_getl_signed_64, bfd_putl64,
9764 bfd_getl32, bfd_getl_signed_32, bfd_putl32,
9765 bfd_getl16, bfd_getl_signed_16, bfd_putl16,
9766 bfd_getl64, bfd_getl_signed_64, bfd_putl64,
9767 bfd_getl32, bfd_getl_signed_32, bfd_putl32,
9768 bfd_getl16, bfd_getl_signed_16, bfd_putl16,
9769
d00dd7dc
AM
9770 { /* bfd_check_format. */
9771 _bfd_dummy_target,
9772 alpha_vms_object_p,
9773 _bfd_vms_lib_alpha_archive_p,
9774 _bfd_dummy_target
9775 },
9776 { /* bfd_set_format. */
9777 _bfd_bool_bfd_false_error,
9778 alpha_vms_mkobject,
9779 _bfd_vms_lib_alpha_mkarchive,
9780 _bfd_bool_bfd_false_error
9781 },
9782 { /* bfd_write_contents. */
9783 _bfd_bool_bfd_false_error,
9784 alpha_vms_write_object_contents,
9785 _bfd_vms_lib_write_archive_contents,
9786 _bfd_bool_bfd_false_error
9787 },
95e34ef7
TG
9788
9789 BFD_JUMP_TABLE_GENERIC (alpha_vms),
9790 BFD_JUMP_TABLE_COPY (vms),
9791 BFD_JUMP_TABLE_CORE (_bfd_nocore),
9792 BFD_JUMP_TABLE_ARCHIVE (_bfd_vms_lib),
9793 BFD_JUMP_TABLE_SYMBOLS (alpha_vms),
9794 BFD_JUMP_TABLE_RELOCS (alpha_vms),
9795 BFD_JUMP_TABLE_WRITE (alpha_vms),
9796 BFD_JUMP_TABLE_LINK (alpha_vms),
9797 BFD_JUMP_TABLE_DYNAMIC (alpha_vms),
9798
9799 NULL,
9800
8185f55c 9801 NULL
95e34ef7 9802};
This page took 1.709244 seconds and 4 git commands to generate.