1 |
/* vms-gsd.c -- BFD back-end for VAX (openVMS/VAX) and |
/* vms-gsd.c -- BFD back-end for VAX (openVMS/VAX) and |
2 |
EVAX (openVMS/Alpha) files. |
EVAX (openVMS/Alpha) files. |
3 |
Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002 |
Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 |
4 |
Free Software Foundation, Inc. |
Free Software Foundation, Inc. |
5 |
|
|
6 |
go and read the openVMS linker manual (esp. appendix B) |
go and read the openVMS linker manual (esp. appendix B) |
358 |
return -1; |
return -1; |
359 |
} |
} |
360 |
old_flags = bfd_getl16 (vms_rec + 2); |
old_flags = bfd_getl16 (vms_rec + 2); |
361 |
section->_raw_size = bfd_getl32 (vms_rec + 4); /* allocation */ |
section->size = bfd_getl32 (vms_rec + 4); /* allocation */ |
362 |
new_flags = vms_secflag_by_name (abfd, vax_section_flags, name, |
new_flags = vms_secflag_by_name (abfd, vax_section_flags, name, |
363 |
section->_raw_size > 0); |
section->size > 0); |
364 |
if (old_flags & EGPS_S_V_REL) |
if (old_flags & EGPS_S_V_REL) |
365 |
new_flags |= SEC_RELOC; |
new_flags |= SEC_RELOC; |
366 |
if (old_flags & GPS_S_M_OVR) |
if (old_flags & GPS_S_M_OVR) |
377 |
if ((base_addr % align_addr) != 0) |
if ((base_addr % align_addr) != 0) |
378 |
base_addr += (align_addr - (base_addr % align_addr)); |
base_addr += (align_addr - (base_addr % align_addr)); |
379 |
section->vma = (bfd_vma)base_addr; |
section->vma = (bfd_vma)base_addr; |
380 |
base_addr += section->_raw_size; |
base_addr += section->size; |
381 |
|
|
382 |
/* global section is common symbol */ |
/* global section is common symbol */ |
383 |
|
|
401 |
if (old_section != 0) |
if (old_section != 0) |
402 |
{ |
{ |
403 |
section->contents = old_section->contents; |
section->contents = old_section->contents; |
404 |
if (section->_raw_size < old_section->_raw_size) |
if (section->size < old_section->size) |
405 |
{ |
{ |
406 |
(*_bfd_error_handler) |
(*_bfd_error_handler) |
407 |
(_("Size mismatch section %s=%lx, %s=%lx"), |
(_("Size mismatch section %s=%lx, %s=%lx"), |
408 |
old_section->name, |
old_section->name, |
409 |
(unsigned long) old_section->_raw_size, |
(unsigned long) old_section->size, |
410 |
section->name, |
section->name, |
411 |
(unsigned long) section->_raw_size); |
(unsigned long) section->size); |
412 |
return -1; |
return -1; |
413 |
} |
} |
414 |
else if (section->_raw_size > old_section->_raw_size) |
else if (section->size > old_section->size) |
415 |
{ |
{ |
416 |
section->contents = ((unsigned char *) |
section->contents = ((unsigned char *) |
417 |
bfd_realloc (old_section->contents, |
bfd_realloc (old_section->contents, |
418 |
section->_raw_size)); |
section->size)); |
419 |
if (section->contents == NULL) |
if (section->contents == NULL) |
420 |
{ |
{ |
421 |
bfd_set_error (bfd_error_no_memory); |
bfd_set_error (bfd_error_no_memory); |
422 |
return -1; |
return -1; |
423 |
} |
} |
424 |
} |
} |
425 |
} |
} |
426 |
else |
else |
427 |
{ |
{ |
428 |
section->contents = ((unsigned char *) |
section->contents = ((unsigned char *) |
429 |
bfd_zmalloc (section->_raw_size)); |
bfd_zmalloc (section->size)); |
430 |
if (section->contents == NULL) |
if (section->contents == NULL) |
431 |
{ |
{ |
432 |
bfd_set_error (bfd_error_no_memory); |
bfd_set_error (bfd_error_no_memory); |
433 |
return -1; |
return -1; |
434 |
} |
} |
435 |
} |
} |
|
section->_cooked_size = section->_raw_size; |
|
436 |
#if VMS_DEBUG |
#if VMS_DEBUG |
437 |
vms_debug (4, "gsd psc %d (%s, flags %04x=%s) ", |
vms_debug (4, "gsd psc %d (%s, flags %04x=%s) ", |
438 |
section->index, name, old_flags, flag2str (gpsflagdesc, old_flags)); |
section->index, name, old_flags, flag2str (gpsflagdesc, old_flags)); |
439 |
vms_debug (4, "%d bytes at 0x%08lx (mem %p)\n", |
vms_debug (4, "%d bytes at 0x%08lx (mem %p)\n", |
440 |
section->_raw_size, section->vma, section->contents); |
section->size, section->vma, section->contents); |
441 |
#endif |
#endif |
442 |
|
|
443 |
gsd_size = vms_rec[8] + 9; |
gsd_size = vms_rec[8] + 9; |
520 |
else |
else |
521 |
psect = vms_rec[value_offset-1]; |
psect = vms_rec[value_offset-1]; |
522 |
|
|
523 |
symbol->section = (asection *)psect; |
symbol->section = (asection *) (size_t) psect; |
524 |
#if VMS_DEBUG |
#if VMS_DEBUG |
525 |
vms_debug(4, "gsd sym def #%d (%s, %d [%p], %04x=%s)\n", abfd->symcount, |
vms_debug(4, "gsd sym def #%d (%s, %d [%p], %04x=%s)\n", abfd->symcount, |
526 |
symbol->name, (int)symbol->section, symbol->section, old_flags, flag2str(gsyflagdesc, old_flags)); |
symbol->name, (int)symbol->section, symbol->section, old_flags, flag2str(gsyflagdesc, old_flags)); |
602 |
if (!section) |
if (!section) |
603 |
return -1; |
return -1; |
604 |
old_flags = bfd_getl16 (vms_rec + 6); |
old_flags = bfd_getl16 (vms_rec + 6); |
605 |
section->_raw_size = bfd_getl32 (vms_rec + 8); /* allocation */ |
section->size = bfd_getl32 (vms_rec + 8); /* allocation */ |
606 |
new_flags = vms_secflag_by_name (abfd, evax_section_flags, name, |
new_flags = vms_secflag_by_name (abfd, evax_section_flags, name, |
607 |
section->_raw_size > 0); |
section->size > 0); |
608 |
if (old_flags & EGPS_S_V_REL) |
if (old_flags & EGPS_S_V_REL) |
609 |
new_flags |= SEC_RELOC; |
new_flags |= SEC_RELOC; |
610 |
if (!bfd_set_section_flags (abfd, section, new_flags)) |
if (!bfd_set_section_flags (abfd, section, new_flags)) |
614 |
if ((base_addr % align_addr) != 0) |
if ((base_addr % align_addr) != 0) |
615 |
base_addr += (align_addr - (base_addr % align_addr)); |
base_addr += (align_addr - (base_addr % align_addr)); |
616 |
section->vma = (bfd_vma)base_addr; |
section->vma = (bfd_vma)base_addr; |
617 |
base_addr += section->_raw_size; |
base_addr += section->size; |
618 |
section->contents = ((unsigned char *) |
section->contents = ((unsigned char *) |
619 |
bfd_zmalloc (section->_raw_size)); |
bfd_zmalloc (section->size)); |
620 |
if (section->contents == NULL) |
if (section->contents == NULL) |
621 |
return -1; |
return -1; |
|
section->_cooked_size = section->_raw_size; |
|
622 |
#if VMS_DEBUG |
#if VMS_DEBUG |
623 |
vms_debug(4, "egsd psc %d (%s, flags %04x=%s) ", |
vms_debug(4, "egsd psc %d (%s, flags %04x=%s) ", |
624 |
section->index, name, old_flags, flag2str(gpsflagdesc, old_flags)); |
section->index, name, old_flags, flag2str(gpsflagdesc, old_flags)); |
625 |
vms_debug(4, "%d bytes at 0x%08lx (mem %p)\n", |
vms_debug(4, "%d bytes at 0x%08lx (mem %p)\n", |
626 |
section->_raw_size, section->vma, section->contents); |
section->size, section->vma, section->contents); |
627 |
#endif |
#endif |
628 |
} |
} |
629 |
break; |
break; |
659 |
} |
} |
660 |
else /* symbol reference */ |
else /* symbol reference */ |
661 |
{ |
{ |
662 |
symbol->name = |
symbol->name = |
663 |
_bfd_vms_save_counted_string (vms_rec+8); |
_bfd_vms_save_counted_string (vms_rec+8); |
664 |
#if VMS_DEBUG |
#if VMS_DEBUG |
665 |
vms_debug(4, "egsd sym ref #%d (%s, %04x=%s)\n", abfd->symcount, |
vms_debug(4, "egsd sym ref #%d (%s, %04x=%s)\n", abfd->symcount, |
666 |
symbol->name, old_flags, flag2str(gsyflagdesc, old_flags)); |
symbol->name, old_flags, flag2str(gsyflagdesc, old_flags)); |
667 |
#endif |
#endif |
668 |
symbol->section = bfd_make_section (abfd, BFD_UND_SECTION_NAME); |
symbol->section = bfd_make_section (abfd, BFD_UND_SECTION_NAME); |
669 |
} |
} |
670 |
|
|
671 |
symbol->flags = new_flags; |
symbol->flags = new_flags; |
672 |
|
|
673 |
/* save symbol in vms_symbol_table */ |
/* save symbol in vms_symbol_table */ |
674 |
|
|
675 |
entry = (vms_symbol_entry *) bfd_hash_lookup (PRIV(vms_symbol_table), symbol->name, true, false); |
entry = (vms_symbol_entry *) bfd_hash_lookup (PRIV(vms_symbol_table), |
676 |
|
symbol->name, |
677 |
|
TRUE, FALSE); |
678 |
if (entry == (vms_symbol_entry *)NULL) |
if (entry == (vms_symbol_entry *)NULL) |
679 |
{ |
{ |
680 |
bfd_set_error (bfd_error_no_memory); |
bfd_set_error (bfd_error_no_memory); |
756 |
while (section != 0) |
while (section != 0) |
757 |
{ |
{ |
758 |
#if VMS_DEBUG |
#if VMS_DEBUG |
759 |
vms_debug (3, "Section #%d %s, %d bytes\n", section->index, section->name, (int)section->_raw_size); |
vms_debug (3, "Section #%d %s, %d bytes\n", section->index, section->name, (int)section->size); |
760 |
#endif |
#endif |
761 |
|
|
762 |
/* 13 bytes egsd, max 31 chars name -> should be 44 bytes */ |
/* 13 bytes egsd, max 31 chars name -> should be 44 bytes */ |
786 |
last_index++; |
last_index++; |
787 |
} |
} |
788 |
|
|
789 |
/* Don't know if this is neccesary for the linker but for now it keeps |
/* Don't know if this is necessary for the linker but for now it keeps |
790 |
vms_slurp_gsd happy */ |
vms_slurp_gsd happy */ |
791 |
|
|
792 |
sname = (char *)section->name; |
sname = (char *)section->name; |
822 |
else |
else |
823 |
{ |
{ |
824 |
new_flags = vms_esecflag_by_name (evax_section_flags, sname, |
new_flags = vms_esecflag_by_name (evax_section_flags, sname, |
825 |
section->_raw_size > 0); |
section->size > 0); |
826 |
} |
} |
827 |
_bfd_vms_output_short (abfd, new_flags); |
_bfd_vms_output_short (abfd, new_flags); |
828 |
_bfd_vms_output_long (abfd, (unsigned long) section->_raw_size); |
_bfd_vms_output_long (abfd, (unsigned long) section->size); |
829 |
_bfd_vms_output_counted (abfd, sname); |
_bfd_vms_output_counted (abfd, sname); |
830 |
_bfd_vms_output_flush (abfd); |
_bfd_vms_output_flush (abfd); |
831 |
|
|
901 |
unsigned long ca_psindx = 0; |
unsigned long ca_psindx = 0; |
902 |
unsigned long psindx; |
unsigned long psindx; |
903 |
|
|
904 |
if (old_flags & BSF_FUNCTION) |
if ((old_flags & BSF_FUNCTION) && symbol->udata.p != NULL) |
905 |
{ |
{ |
906 |
code_address = ((asymbol *) (symbol->udata.p))->value; |
code_address = ((asymbol *) (symbol->udata.p))->value; |
907 |
ca_psindx = ((asymbol *) (symbol->udata.p))->section->index; |
ca_psindx = ((asymbol *) (symbol->udata.p))->section->index; |