aboutsummaryrefslogtreecommitdiff
path: root/gas/write.c
diff options
context:
space:
mode:
authorKen Raeburn <raeburn@cygnus>1994-12-31 00:08:40 +0000
committerKen Raeburn <raeburn@cygnus>1994-12-31 00:08:40 +0000
commitcd3b81bd4cda2f9e04cca02ea6539be322a46986 (patch)
tree3ec294699834a687853664c804eb37fc98da8ab1 /gas/write.c
parente12533e3e9b498fdd0702d5c1719eaf0bf05e5a6 (diff)
downloadgdb-cd3b81bd4cda2f9e04cca02ea6539be322a46986.zip
gdb-cd3b81bd4cda2f9e04cca02ea6539be322a46986.tar.gz
gdb-cd3b81bd4cda2f9e04cca02ea6539be322a46986.tar.bz2
Handle .space directive with non-constant operand:
* read.c (s_space): Rewrite to handle general expressions. Generate rs_space frags for non-constant values. * write.c (cvt_frag_to_fill): Treat rs_align_code and rs_space like rs_align and rs_org. Verify that fr_offset is non-negative, and force frag type to rs_fill only after assertion checks. (relax_segment): Treat rs_align_code like rs_align. Treat rs_space like rs_org in the first switch; in the second, force the operand to a constant, and use it for the growth size.
Diffstat (limited to 'gas/write.c')
-rw-r--r--gas/write.c29
1 files changed, 26 insertions, 3 deletions
diff --git a/gas/write.c b/gas/write.c
index b362670..7cdf2c2 100644
--- a/gas/write.c
+++ b/gas/write.c
@@ -419,15 +419,18 @@ cvt_frag_to_fill (headers, fragP)
switch (fragP->fr_type)
{
case rs_align:
+ case rs_align_code:
case rs_org:
+ case rs_space:
#ifdef HANDLE_ALIGN
HANDLE_ALIGN (fragP);
#endif
- fragP->fr_type = rs_fill;
know (fragP->fr_next != NULL);
fragP->fr_offset = (fragP->fr_next->fr_address
- fragP->fr_address
- fragP->fr_fix) / fragP->fr_var;
+ assert (fragP->fr_offset >= 0);
+ fragP->fr_type = rs_fill;
break;
case rs_fill:
@@ -625,8 +628,8 @@ adjust_reloc_syms (abfd, sec, xxx)
md_estimate_size_before_relax in tc-mips.c uses this test
as well, so if you change this code you should look at that
code. */
- if (symsec == &bfd_und_section
- || symsec == &bfd_abs_section
+ if (bfd_is_und_section (symsec)
+ || bfd_is_abs_section (symsec)
|| bfd_is_com_section (symsec))
{
fixp->fx_addsy->sy_used_in_reloc = 1;
@@ -1731,6 +1734,7 @@ relax_segment (segment_frag_root, segment)
break;
case rs_align:
+ case rs_align_code:
{
int offset = relax_align (address, (int) fragP->fr_offset);
if (offset % fragP->fr_var != 0)
@@ -1744,6 +1748,7 @@ relax_segment (segment_frag_root, segment)
break;
case rs_org:
+ case rs_space:
/* Assume .org is nugatory. It will grow with 1st relax. */
break;
@@ -1859,6 +1864,7 @@ relax_segment (segment_frag_root, segment)
} /* case rs_broken_word */
#endif
case rs_align:
+ case rs_align_code:
growth = (relax_align ((relax_addressT) (address
+ fragP->fr_fix),
(int) offset)
@@ -1895,6 +1901,23 @@ relax_segment (segment_frag_root, segment)
growth -= stretch; /* This is an absolute growth factor */
break;
+ case rs_space:
+ if (symbolP)
+ {
+ growth = S_GET_VALUE (symbolP);
+ if (symbolP->sy_frag != &zero_address_frag)
+ as_bad (".space specifies non-absolute value");
+ fragP->fr_symbol = 0;
+ if (growth < 0)
+ {
+ as_warn (".space or .fill with negative value, ignored");
+ growth = 0;
+ }
+ }
+ else
+ growth = 0;
+ break;
+
case rs_machine_dependent:
#ifdef md_relax_frag
growth = md_relax_frag (fragP, stretch);