aboutsummaryrefslogtreecommitdiff
path: root/gas/write.c
diff options
context:
space:
mode:
authorKen Raeburn <raeburn@cygnus>1993-08-05 21:21:30 +0000
committerKen Raeburn <raeburn@cygnus>1993-08-05 21:21:30 +0000
commitb23f674392be751f8a868d222552154e6cc511f4 (patch)
treea37c0e56925a3c448ca9f7ec68b979051c67d468 /gas/write.c
parentb12193c0730e9e7cc6a4df12271099a579be6f18 (diff)
downloadgdb-b23f674392be751f8a868d222552154e6cc511f4.zip
gdb-b23f674392be751f8a868d222552154e6cc511f4.tar.gz
gdb-b23f674392be751f8a868d222552154e6cc511f4.tar.bz2
(write_object_file): Test DEBUG_SYMS instead of DEBUG for verifying sym chain.
(merge_data_into_text, relax_and_size_all_segments): New fns, split out from write_object_file.
Diffstat (limited to 'gas/write.c')
-rw-r--r--gas/write.c252
1 files changed, 131 insertions, 121 deletions
diff --git a/gas/write.c b/gas/write.c
index 67db922..bcef9d0 100644
--- a/gas/write.c
+++ b/gas/write.c
@@ -59,12 +59,12 @@ int magic_number_for_object_file = DEFAULT_MAGIC_NUMBER_FOR_OBJECT_FILE;
#endif /* BFD_ASSEMBLER */
#ifdef BFD_ASSEMBLER
-static fixS *fix_new_internal PARAMS ((fragS *, int where, short int size,
+static fixS *fix_new_internal PARAMS ((fragS *, int where, int size,
symbolS *add, symbolS *sub,
offsetT offset, int pcrel,
bfd_reloc_code_real_type r_type));
#else
-static fixS *fix_new_internal PARAMS ((fragS *, int where, short int size,
+static fixS *fix_new_internal PARAMS ((fragS *, int where, int size,
symbolS *add, symbolS *sub,
offsetT offset, int pcrel,
int r_type));
@@ -83,7 +83,7 @@ fix_new_internal (frag, where, size, add_symbol, sub_symbol, offset, pcrel,
r_type)
fragS *frag; /* Which frag? */
int where; /* Where in that frag? */
- short int size; /* 1, 2, or 4 usually. */
+ int size; /* 1, 2, or 4 usually. */
symbolS *add_symbol; /* X_add_symbol. */
symbolS *sub_symbol; /* X_op_symbol. */
offsetT offset; /* X_add_number. */
@@ -200,6 +200,11 @@ fix_new_exp (frag, where, size, exp, pcrel, r_type)
case O_absent:
break;
+ case O_uminus:
+ sub = exp->X_add_symbol;
+ off = exp->X_add_number;
+ break;
+
case O_subtract:
sub = exp->X_op_symbol;
/* Fall through. */
@@ -709,11 +714,6 @@ write_contents (abfd, sec, xxx)
if (! (bfd_get_section_flags (abfd, sec) & SEC_HAS_CONTENTS))
return;
-#if 0 /* Who cares? Let the first call, below, do it. */
- /* Force calculations (size, vma) to get done. */
- bfd_set_section_contents (stdoutput, sec, "", 0, (addressT) 0);
-#endif
-
for (frags = seginfo->frchainP->frch_root;
frags;
frags = frags->fr_next)
@@ -749,6 +749,125 @@ write_contents (abfd, sec, xxx)
}
#endif
+static void
+merge_data_into_text ()
+{
+#ifdef BFD_ASSEMBLER
+ seg_info (text_section)->frchainP->frch_last->fr_next =
+ seg_info (data_section)->frchainP->frch_root;
+ seg_info (text_section)->frchainP->frch_last =
+ seg_info (data_section)->frchainP->frch_last;
+ seg_info (data_section)->frchainP = 0;
+#else
+ fixS *tmp;
+
+ text_last_frag->fr_next = data_frag_root;
+ text_last_frag = data_last_frag;
+ data_last_frag = NULL;
+ data_frag_root = NULL;
+ if (text_fix_root)
+ {
+ for (tmp = text_fix_root; tmp->fx_next; tmp = tmp->fx_next);;
+ tmp->fx_next = data_fix_root;
+ text_fix_tail = data_fix_tail;
+ }
+ else
+ text_fix_root = data_fix_root;
+ data_fix_root = NULL;
+#endif
+}
+
+#if !defined (BFD_ASSEMBLER) && !defined (BFD)
+static void
+relax_and_size_all_segments ()
+{
+ relax_segment (text_frag_root, SEG_TEXT);
+ relax_segment (data_frag_root, SEG_DATA);
+ relax_segment (bss_frag_root, SEG_BSS);
+ /*
+ * Now the addresses of frags are correct within the segment.
+ */
+
+ know (text_last_frag->fr_type == rs_fill && text_last_frag->fr_offset == 0);
+ H_SET_TEXT_SIZE (&headers, text_last_frag->fr_address);
+ text_last_frag->fr_address = H_GET_TEXT_SIZE (&headers);
+
+ /*
+ * Join the 2 segments into 1 huge segment.
+ * To do this, re-compute every rn_address in the SEG_DATA frags.
+ * Then join the data frags after the text frags.
+ *
+ * Determine a_data [length of data segment].
+ */
+ if (data_frag_root)
+ {
+ register relax_addressT slide;
+
+ know ((text_last_frag->fr_type == rs_fill) && (text_last_frag->fr_offset == 0));
+
+ H_SET_DATA_SIZE (&headers, data_last_frag->fr_address);
+ data_last_frag->fr_address = H_GET_DATA_SIZE (&headers);
+ slide = H_GET_TEXT_SIZE (&headers); /* & in file of the data segment. */
+#ifdef OBJ_BOUT
+#define RoundUp(N,S) (((N)+(S)-1)&-(S))
+ /* For b.out: If the data section has a strict alignment
+ requirement, its load address in the .o file will be
+ rounded up from the size of the text section. These
+ two values are *not* the same! Similarly for the bss
+ section.... */
+ slide = RoundUp (slide, 1 << section_alignment[SEG_DATA]);
+#endif
+
+ for (fragP = data_frag_root; fragP; fragP = fragP->fr_next)
+ {
+ fragP->fr_address += slide;
+ } /* for each data frag */
+
+ know (text_last_frag != 0);
+ text_last_frag->fr_next = data_frag_root;
+ }
+ else
+ {
+ H_SET_DATA_SIZE (&headers, 0);
+ }
+
+#ifdef OBJ_BOUT
+ /* See above comments on b.out data section address. */
+ {
+ long bss_vma;
+ if (data_last_frag == 0)
+ bss_vma = H_GET_TEXT_SIZE (&headers);
+ else
+ bss_vma = data_last_frag->fr_address;
+ bss_vma = RoundUp (bss_vma, 1 << section_alignment[SEG_BSS]);
+ bss_address_frag.fr_address = bss_vma;
+ }
+#else /* ! OBJ_BOUT */
+ bss_address_frag.fr_address = (H_GET_TEXT_SIZE (&headers) +
+ H_GET_DATA_SIZE (&headers));
+
+
+ /* Slide all the frags */
+ if (bss_frag_root)
+ {
+ relax_addressT slide = bss_address_frag.fr_address;
+
+ for (fragP = bss_frag_root; fragP; fragP = fragP->fr_next)
+ {
+ fragP->fr_address += slide;
+ } /* for each bss frag */
+ }
+
+#endif /* ! OBJ_BOUT */
+
+ if (bss_last_frag)
+ H_SET_BSS_SIZE (&headers,
+ bss_last_frag->fr_address - bss_frag_root->fr_address);
+ else
+ H_SET_BSS_SIZE (&headers, 0);
+}
+#endif /* ! BFD_ASSEMBLER && ! BFD */
+
#if defined (BFD_ASSEMBLER) || !defined (BFD)
void
@@ -756,7 +875,6 @@ write_object_file ()
{
register struct frchain *frchainP; /* Track along all frchains. */
register fragS *fragP; /* Track along all frags. */
-
#if !defined (BFD_ASSEMBLER) && !defined (OBJ_VMS)
long object_file_size;
#endif
@@ -824,8 +942,6 @@ write_object_file ()
frag_wane (frag_now);
frag_now->fr_fix = 0;
know (frag_now->fr_next == NULL);
- /* know( frags . obstack_c_base == frags . obstack_c_next_free ); */
- /* Above shows we haven't left a half-completed object on obstack. */
}
/* From now on, we don't care about sub-segments. Build one frag chain
@@ -865,120 +981,14 @@ write_object_file ()
#if !defined (OBJ_AOUT) || defined (BFD_ASSEMBLER)
if (flagseen['R'])
{
-#ifdef BFD_ASSEMBLER
- seg_info (text_section)->frchainP->frch_last->fr_next =
- seg_info (data_section)->frchainP->frch_root;
- seg_info (text_section)->frchainP->frch_last =
- seg_info (data_section)->frchainP->frch_last;
- seg_info (data_section)->frchainP = 0;
-#else
- fixS *tmp;
-
- text_last_frag->fr_next = data_frag_root;
- text_last_frag = data_last_frag;
- data_last_frag = NULL;
- data_frag_root = NULL;
- if (text_fix_root)
- {
- for (tmp = text_fix_root; tmp->fx_next; tmp = tmp->fx_next);;
- tmp->fx_next = data_fix_root;
- text_fix_tail = data_fix_tail;
- }
- else
- text_fix_root = data_fix_root;
- data_fix_root = NULL;
-#endif
+ merge_data_into_text ();
}
#endif
#ifdef BFD_ASSEMBLER
-
bfd_map_over_sections (stdoutput, relax_and_size_seg, (char *) 0);
#else
- relax_segment (text_frag_root, SEG_TEXT);
- relax_segment (data_frag_root, SEG_DATA);
- relax_segment (bss_frag_root, SEG_BSS);
- /*
- * Now the addresses of frags are correct within the segment.
- */
-
- know (text_last_frag->fr_type == rs_fill && text_last_frag->fr_offset == 0);
- H_SET_TEXT_SIZE (&headers, text_last_frag->fr_address);
- text_last_frag->fr_address = H_GET_TEXT_SIZE (&headers);
-
- /*
- * Join the 2 segments into 1 huge segment.
- * To do this, re-compute every rn_address in the SEG_DATA frags.
- * Then join the data frags after the text frags.
- *
- * Determine a_data [length of data segment].
- */
- if (data_frag_root)
- {
- register relax_addressT slide;
-
- know ((text_last_frag->fr_type == rs_fill) && (text_last_frag->fr_offset == 0));
-
- H_SET_DATA_SIZE (&headers, data_last_frag->fr_address);
- data_last_frag->fr_address = H_GET_DATA_SIZE (&headers);
- slide = H_GET_TEXT_SIZE (&headers); /* & in file of the data segment. */
-#ifdef OBJ_BOUT
-#define RoundUp(N,S) (((N)+(S)-1)&-(S))
- /* For b.out: If the data section has a strict alignment
- requirement, its load address in the .o file will be
- rounded up from the size of the text section. These
- two values are *not* the same! Similarly for the bss
- section.... */
- slide = RoundUp (slide, 1 << section_alignment[SEG_DATA]);
-#endif
-
- for (fragP = data_frag_root; fragP; fragP = fragP->fr_next)
- {
- fragP->fr_address += slide;
- } /* for each data frag */
-
- know (text_last_frag != 0);
- text_last_frag->fr_next = data_frag_root;
- }
- else
- {
- H_SET_DATA_SIZE (&headers, 0);
- }
-
-#ifdef OBJ_BOUT
- /* See above comments on b.out data section address. */
- {
- long bss_vma;
- if (data_last_frag == 0)
- bss_vma = H_GET_TEXT_SIZE (&headers);
- else
- bss_vma = data_last_frag->fr_address;
- bss_vma = RoundUp (bss_vma, 1 << section_alignment[SEG_BSS]);
- bss_address_frag.fr_address = bss_vma;
- }
-#else /* ! OBJ_BOUT */
- bss_address_frag.fr_address = (H_GET_TEXT_SIZE (&headers) +
- H_GET_DATA_SIZE (&headers));
-
-
- /* Slide all the frags */
- if (bss_frag_root)
- {
- relax_addressT slide = bss_address_frag.fr_address;
-
- for (fragP = bss_frag_root; fragP; fragP = fragP->fr_next)
- {
- fragP->fr_address += slide;
- } /* for each bss frag */
- }
-
-#endif /* ! OBJ_BOUT */
-
- if (bss_last_frag)
- H_SET_BSS_SIZE (&headers,
- bss_last_frag->fr_address - bss_frag_root->fr_address);
- else
- H_SET_BSS_SIZE (&headers, 0);
+ relax_and_size_all_segments ();
#endif /* BFD_ASSEMBLER */
#ifndef BFD_ASSEMBLER
@@ -1308,7 +1318,7 @@ write_object_file ()
punt_it:
prev = symbol_previous (symp);
next = symbol_next (symp);
-#ifdef DEBUG
+#ifdef DEBUG_SYMS
verify_symbol_chain_2 (symp);
#endif
if (prev)
@@ -1324,7 +1334,7 @@ write_object_file ()
symbol_previous (next) = prev;
else
symbol_lastP = prev;
-#ifdef DEBUG
+#ifdef DEBUG_SYMS
if (prev)
verify_symbol_chain_2 (prev);
else if (next)