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