1 /* BFD back-end for mmo objects (MMIX-specific object-format).
2    Copyright (C) 2001-2021 Free Software Foundation, Inc.
3    Written by Hans-Peter Nilsson (hp@bitrange.com).
4    Infrastructure and other bits originally copied from srec.c and
5    binary.c.
6 
7    This file is part of BFD, the Binary File Descriptor library.
8 
9    This program is free software; you can redistribute it and/or modify
10    it under the terms of the GNU General Public License as published by
11    the Free Software Foundation; either version 3 of the License, or
12    (at your option) any later version.
13 
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18 
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
22    MA 02110-1301, USA.  */
23 
24 
25 /*
26 SECTION
27 	mmo backend
28 
29 	The mmo object format is used exclusively together with Professor
30 	Donald E.@: Knuth's educational 64-bit processor MMIX.  The simulator
31 	@command{mmix} which is available at
32 	@url{http://mmix.cs.hm.edu/src/index.html}
33 	understands this format.  That package also includes a combined
34 	assembler and linker called @command{mmixal}.  The mmo format has
35 	no advantages feature-wise compared to e.g. ELF.  It is a simple
36 	non-relocatable object format with no support for archives or
37 	debugging information, except for symbol value information and
38 	line numbers (which is not yet implemented in BFD).  See
39 	@url{http://mmix.cs.hm.edu/} for more
40 	information about MMIX.  The ELF format is used for intermediate
41 	object files in the BFD implementation.
42 
43 @c We want to xref the symbol table node.  A feature in "chew"
44 @c requires that "commands" do not contain spaces in the
45 @c arguments.  Hence the hyphen in "Symbol-table".
46 @menu
47 @* File layout::
48 @* Symbol-table::
49 @* mmo section mapping::
50 @end menu
51 
52 INODE
53 File layout, Symbol-table, mmo, mmo
54 SUBSECTION
55 	File layout
56 
57 	The mmo file contents is not partitioned into named sections as
58 	with e.g.@: ELF.  Memory areas is formed by specifying the
59 	location of the data that follows.  Only the memory area
60 	@samp{0x0000@dots{}00} to @samp{0x01ff@dots{}ff} is executable, so
61 	it is used for code (and constants) and the area
62 	@samp{0x2000@dots{}00} to @samp{0x20ff@dots{}ff} is used for
63 	writable data.  @xref{mmo section mapping}.
64 
65 	There is provision for specifying ``special data'' of 65536
66 	different types.  We use type 80 (decimal), arbitrarily chosen the
67 	same as the ELF <<e_machine>> number for MMIX, filling it with
68 	section information normally found in ELF objects. @xref{mmo
69 	section mapping}.
70 
71 	Contents is entered as 32-bit words, xor:ed over previous
72 	contents, always zero-initialized.  A word that starts with the
73 	byte @samp{0x98} forms a command called a @samp{lopcode}, where
74 	the next byte distinguished between the thirteen lopcodes.  The
75 	two remaining bytes, called the @samp{Y} and @samp{Z} fields, or
76 	the @samp{YZ} field (a 16-bit big-endian number), are used for
77 	various purposes different for each lopcode.  As documented in
78 	@url{http://mmix.cs.hm.edu/doc/mmixal.pdf},
79 	the lopcodes are:
80 
81 	@table @code
82 	@item lop_quote
83 	0x98000001.  The next word is contents, regardless of whether it
84 	starts with 0x98 or not.
85 
86 	@item lop_loc
87 	0x9801YYZZ, where @samp{Z} is 1 or 2.  This is a location
88 	directive, setting the location for the next data to the next
89 	32-bit word (for @math{Z = 1}) or 64-bit word (for @math{Z = 2}),
90 	plus @math{Y * 2^56}.  Normally @samp{Y} is 0 for the text segment
91 	and 2 for the data segment.  Beware that the low bits of non-
92 	tetrabyte-aligned values are silently discarded when being
93 	automatically incremented and when storing contents (in contrast
94 	to e.g. its use as current location when followed by lop_fixo
95 	et al before the next possibly-quoted tetrabyte contents).
96 
97 	@item lop_skip
98 	0x9802YYZZ.  Increase the current location by @samp{YZ} bytes.
99 
100 	@item lop_fixo
101 	0x9803YYZZ, where @samp{Z} is 1 or 2.  Store the current location
102 	as 64 bits into the location pointed to by the next 32-bit
103 	(@math{Z = 1}) or 64-bit (@math{Z = 2}) word, plus @math{Y *
104 	2^56}.
105 
106 	@item lop_fixr
107 	0x9804YYZZ.  @samp{YZ} is stored into the current location plus
108 	@math{2 - 4 * YZ}.
109 
110 	@item lop_fixrx
111 	0x980500ZZ.  @samp{Z} is 16 or 24.  A value @samp{L} derived from
112 	the following 32-bit word are used in a manner similar to
113 	@samp{YZ} in lop_fixr: it is xor:ed into the current location
114 	minus @math{4 * L}.  The first byte of the word is 0 or 1.  If it
115 	is 1, then @math{L = (@var{lowest 24 bits of word}) - 2^Z}, if 0,
116 	then @math{L = (@var{lowest 24 bits of word})}.
117 
118 	@item lop_file
119 	0x9806YYZZ.  @samp{Y} is the file number, @samp{Z} is count of
120 	32-bit words.  Set the file number to @samp{Y} and the line
121 	counter to 0.  The next @math{Z * 4} bytes contain the file name,
122 	padded with zeros if the count is not a multiple of four.  The
123 	same @samp{Y} may occur multiple times, but @samp{Z} must be 0 for
124 	all but the first occurrence.
125 
126 	@item lop_line
127 	0x9807YYZZ.  @samp{YZ} is the line number.  Together with
128 	lop_file, it forms the source location for the next 32-bit word.
129 	Note that for each non-lopcode 32-bit word, line numbers are
130 	assumed incremented by one.
131 
132 	@item lop_spec
133 	0x9808YYZZ.  @samp{YZ} is the type number.  Data until the next
134 	lopcode other than lop_quote forms special data of type @samp{YZ}.
135 	@xref{mmo section mapping}.
136 
137 	Other types than 80, (or type 80 with a content that does not
138 	parse) is stored in sections named <<.MMIX.spec_data.@var{n}>>
139 	where @var{n} is the @samp{YZ}-type.  The flags for such a
140 	sections say not to allocate or load the data.  The vma is 0.
141 	Contents of multiple occurrences of special data @var{n} is
142 	concatenated to the data of the previous lop_spec @var{n}s.  The
143 	location in data or code at which the lop_spec occurred is lost.
144 
145 	@item lop_pre
146 	0x980901ZZ.  The first lopcode in a file.  The @samp{Z} field forms the
147 	length of header information in 32-bit words, where the first word
148 	tells the time in seconds since @samp{00:00:00 GMT Jan 1 1970}.
149 
150 	@item lop_post
151 	0x980a00ZZ.  @math{Z > 32}.  This lopcode follows after all
152 	content-generating lopcodes in a program.  The @samp{Z} field
153 	denotes the value of @samp{rG} at the beginning of the program.
154 	The following @math{256 - Z} big-endian 64-bit words are loaded
155 	into global registers @samp{$G} @dots{} @samp{$255}.
156 
157 	@item lop_stab
158 	0x980b0000.  The next-to-last lopcode in a program.  Must follow
159 	immediately after the lop_post lopcode and its data.  After this
160 	lopcode follows all symbols in a compressed format
161 	(@pxref{Symbol-table}).
162 
163 	@item lop_end
164 	0x980cYYZZ.  The last lopcode in a program.  It must follow the
165 	lop_stab lopcode and its data.  The @samp{YZ} field contains the
166 	number of 32-bit words of symbol table information after the
167 	preceding lop_stab lopcode.
168 	@end table
169 
170 	Note that the lopcode "fixups"; <<lop_fixr>>, <<lop_fixrx>> and
171 	<<lop_fixo>> are not generated by BFD, but are handled.  They are
172 	generated by <<mmixal>>.
173 
174 EXAMPLE
175 	This trivial one-label, one-instruction file:
176 
177 | :Main TRAP 1,2,3
178 
179 	can be represented this way in mmo:
180 
181 | 0x98090101 - lop_pre, one 32-bit word with timestamp.
182 | <timestamp>
183 | 0x98010002 - lop_loc, text segment, using a 64-bit address.
184 |              Note that mmixal does not emit this for the file above.
185 | 0x00000000 - Address, high 32 bits.
186 | 0x00000000 - Address, low 32 bits.
187 | 0x98060002 - lop_file, 2 32-bit words for file-name.
188 | 0x74657374 - "test"
189 | 0x2e730000 - ".s\0\0"
190 | 0x98070001 - lop_line, line 1.
191 | 0x00010203 - TRAP 1,2,3
192 | 0x980a00ff - lop_post, setting $255 to 0.
193 | 0x00000000
194 | 0x00000000
195 | 0x980b0000 - lop_stab for ":Main" = 0, serial 1.
196 | 0x203a4040   @xref{Symbol-table}.
197 | 0x10404020
198 | 0x4d206120
199 | 0x69016e00
200 | 0x81000000
201 | 0x980c0005 - lop_end; symbol table contained five 32-bit words.  */
202 
203 #include "sysdep.h"
204 #include "bfd.h"
205 #include "libbfd.h"
206 #include "libiberty.h"
207 #include "elf/mmix.h"
208 #include "opcode/mmix.h"
209 
210 #define LOP 0x98u
211 #define LOP_QUOTE 0
212 #define LOP_LOC 1
213 #define LOP_SKIP 2
214 #define LOP_FIXO 3
215 #define LOP_FIXR 4
216 #define LOP_FIXRX 5
217 #define LOP_FILE 6
218 #define LOP_LINE 7
219 #define LOP_SPEC 8
220 #define LOP_PRE 9
221 #define LOP_POST 10
222 #define LOP_STAB 11
223 #define LOP_END 12
224 
225 #define LOP_QUOTE_NEXT ((LOP << 24) | (LOP_QUOTE << 16) | 1)
226 #define SPEC_DATA_SECTION 80
227 #define LOP_SPEC_SECTION \
228  ((LOP << 24) | (LOP_SPEC << 16) | SPEC_DATA_SECTION)
229 
230 /* Must be a power of two.  If you change this to be >= 64k, you need a
231    new test-case; the ld test b-loc64k.d touches chunk-size problem areas.  */
232 #define MMO_SEC_CONTENTS_CHUNK_SIZE (1 << 15)
233 
234 /* An arbitrary number for the maximum length section name size.  */
235 #define MAX_SECTION_NAME_SIZE (1024 * 1024)
236 
237 /* A quite arbitrary number for the maximum length section size.  */
238 #define MAX_ARTIFICIAL_SECTION_SIZE (1024 * 1024 * 1024)
239 
240 #define MMO3_WCHAR 0x80
241 #define MMO3_LEFT 0x40
242 #define MMO3_MIDDLE 0x20
243 #define MMO3_RIGHT 0x10
244 #define MMO3_TYPEBITS 0xf
245 #define MMO3_REGQUAL_BITS 0xf
246 #define MMO3_UNDEF 2
247 #define MMO3_DATA 8
248 #define MMO3_SYMBITS 0x2f
249 
250 /* Put these everywhere in new code.  */
251 #define FATAL_DEBUG						\
252  _bfd_abort (__FILE__, __LINE__,				\
253 	     "Internal: Non-debugged code (test-case missing)")
254 
255 #define BAD_CASE(x)				\
256  _bfd_abort (__FILE__, __LINE__,		\
257 	     "bad case for " #x)
258 
259 enum mmo_sym_type { mmo_reg_sym, mmo_undef_sym, mmo_data_sym, mmo_abs_sym};
260 
261 /* When scanning the mmo file, a linked list of mmo_symbol
262    structures is built to represent the symbol table (if there is
263    one).  */
264 
265 struct mmo_symbol
266   {
267     struct mmo_symbol *next;
268     char *name;
269     bfd_vma value;
270     enum mmo_sym_type sym_type;
271     unsigned int serno;
272   };
273 
274 struct mmo_data_list_struct
275   {
276     struct mmo_data_list_struct *next;
277     bfd_vma where;
278     bfd_size_type size;
279     bfd_size_type allocated_size;
280     bfd_byte data[1];
281   };
282 
283 typedef struct mmo_data_list_struct mmo_data_list_type;
284 
285 struct mmo_symbol_trie
286   {
287     struct mmo_symbol_trie *left;
288     struct mmo_symbol_trie *right;
289     struct mmo_symbol_trie *middle;
290 
291     bfd_byte symchar;
292 
293     /* A zero name means there's nothing here.  */
294     struct mmo_symbol sym;
295   };
296 
297 /* The mmo tdata information.  */
298 
299 struct mmo_data_struct
300   {
301     struct mmo_symbol *symbols;
302     struct mmo_symbol *symtail;
303     asymbol *csymbols;
304 
305     /* File representation of time (NULL) when this file was created.  */
306     bfd_byte created[4];
307 
308     /* When we're reading bytes recursively, check this occasionally.
309        Also holds write errors.  */
310     bool have_error;
311 
312     /* Max symbol length that may appear in the lop_stab table.  Note that
313        this table might just hold a subset of symbols for not-really large
314        programs, as it can only be 65536 * 4 bytes large.  */
315     int max_symbol_length;
316 
317     /* Here's the symbol we build in lop_stab.  */
318     char *lop_stab_symbol;
319 
320     /* Index into lop_stab_symbol for the next character when parsing the
321        symbol information.  */
322     int symbol_position;
323 
324     /* When creating arbitrary sections, we need to count section numbers.  */
325     int sec_no;
326 
327     /* When writing or reading byte-wise, we need to count the bytes
328        within a 32-bit word.  */
329     int byte_no;
330 
331     /* We also need a buffer to hold the bytes we count reading or writing.  */
332     bfd_byte buf[4];
333 
334     /* Whether we've calculated symbol consistency requirement yet.  We do this
335        when-needed, which must be at some time after all section
336        contents is known.  */
337     bool symbol_consistency_override_calculated;
338 
339     /* Whether to consistency-check symbol values, in particular "Main".  */
340     bool ignore_symbol_consistency;
341   };
342 
343 typedef struct mmo_data_struct tdata_type;
344 
345 struct mmo_section_data_struct
346   {
347     mmo_data_list_type *head;
348     mmo_data_list_type *tail;
349   };
350 
351 #define mmo_section_data(sec) \
352   ((struct mmo_section_data_struct *) (sec)->used_by_bfd)
353 
354 /* These structures are used in bfd_map_over_sections constructs.  */
355 
356 /* Used when writing out sections; all but the register contents section
357    which is stored in reg_section.  */
358 struct mmo_write_sec_info
359   {
360     asection *reg_section;
361     bool retval;
362   };
363 
364 /* Used when trying to find a section corresponding to addr.  */
365 struct mmo_find_sec_info
366   {
367     asection *sec;
368     bfd_vma addr;
369   };
370 
371 static bool mmo_bfd_copy_private_bfd_data (bfd *, bfd *);
372 static void mmo_write_section_unless_reg_contents (bfd *, asection *, void *);
373 static void mmo_find_sec_w_addr (bfd *, asection *, void *);
374 static void mmo_find_sec_w_addr_grow (bfd *, asection *, void *);
375 static asection *mmo_make_section (bfd *, const char *);
376 static void mmo_get_symbol_info (bfd *, asymbol *, symbol_info *);
377 static void mmo_print_symbol (bfd *, void *, asymbol *,
378 			      bfd_print_symbol_type);
379 static void mmo_init (void);
380 static bool mmo_mkobject (bfd *);
381 static bool mmo_scan (bfd *);
382 static asection *mmo_decide_section (bfd *, bfd_vma);
383 static asection *mmo_get_generic_spec_data_section (bfd *, int);
384 static asection *mmo_get_spec_section (bfd *, int);
385 static INLINE bfd_byte *mmo_get_loc (asection *, bfd_vma, int);
386 static void mmo_xore_64 (asection *, bfd_vma vma, bfd_vma value);
387 static void mmo_xore_32 (asection *, bfd_vma vma, unsigned int);
388 static void mmo_xore_16 (asection *, bfd_vma vma, unsigned int);
389 static bfd_cleanup mmo_object_p (bfd *);
390 static void mmo_map_set_sizes (bfd *, asection *, void *);
391 static bool mmo_get_symbols (bfd *);
392 static bool mmo_create_symbol (bfd *, const char *, bfd_vma,
393 			       enum mmo_sym_type, unsigned int);
394 static bool mmo_get_section_contents (bfd *, asection *, void *,
395 				      file_ptr, bfd_size_type);
396 static long mmo_get_symtab_upper_bound (bfd *);
397 static long mmo_canonicalize_symtab (bfd *, asymbol **);
398 static void mmo_get_symbol_info (bfd *, asymbol *, symbol_info *);
399 static void mmo_print_symbol (bfd *, void *, asymbol *,
400 			      bfd_print_symbol_type);
401 static bool mmo_set_section_contents (bfd *, sec_ptr, const void *,
402 				      file_ptr, bfd_size_type);
403 static int mmo_sizeof_headers (bfd *, struct bfd_link_info *);
404 static bool mmo_internal_write_header (bfd *);
405 static bool mmo_internal_write_post (bfd *, int, asection *);
406 static bool mmo_internal_add_3_sym (bfd *, struct mmo_symbol_trie *,
407 					   const struct mmo_symbol *);
408 static unsigned int mmo_internal_3_length (bfd *, struct mmo_symbol_trie *);
409 static void mmo_internal_3_dump (bfd *, struct mmo_symbol_trie *);
410 static void mmo_beb128_out (bfd *, int, int);
411 static bool mmo_internal_write_section (bfd *, asection *);
412 static void mmo_write_tetra (bfd *, unsigned int);
413 static void mmo_write_tetra_raw (bfd *, unsigned int);
414 static void mmo_write_octa (bfd *, bfd_vma);
415 static void mmo_write_octa_raw (bfd *, bfd_vma);
416 static bool mmo_write_chunk (bfd *, const bfd_byte *, unsigned int);
417 static bool mmo_flush_chunk (bfd *);
418 static bool mmo_write_loc_chunk (bfd *, bfd_vma, const bfd_byte *,
419 				 unsigned int, bfd_vma *);
420 static bool mmo_write_chunk_list (bfd *, mmo_data_list_type *);
421 static bool mmo_write_loc_chunk_list (bfd *, mmo_data_list_type *);
422 static bool mmo_write_symbols_and_terminator (bfd *);
423 static flagword mmo_sec_flags_from_bfd_flags (flagword);
424 static flagword bfd_sec_flags_from_mmo_flags (flagword);
425 static bfd_byte mmo_get_byte (bfd *);
426 static void mmo_write_byte (bfd *, bfd_byte);
427 static bool mmo_new_section_hook (bfd *, asection *);
428 static int mmo_sort_mmo_symbols (const void *, const void *);
429 static bool mmo_write_object_contents (bfd *);
430 static bool mmo_write_section_description (bfd *, asection *);
431 static bool mmo_has_leading_or_trailing_zero_tetra_p (bfd *, asection *);
432 
433 static const char
434 valid_mmo_symbol_character_set[] =
435 {
436   'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
437   'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
438   'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
439   'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
440   '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
441   ':', '_', 126, 127, 128, 129,
442   130, 131, 132, 133, 134, 135, 136, 137, 138, 139,
443   140, 141, 142, 143, 144, 145, 146, 147, 148, 149,
444   150, 151, 152, 153, 154, 155, 156, 157, 158, 159,
445   160, 161, 162, 163, 164, 165, 166, 167, 168, 169,
446   170, 171, 172, 173, 174, 175, 176, 177, 178, 179,
447   180, 181, 182, 183, 184, 185, 186, 187, 188, 189,
448   190, 191, 192, 193, 194, 195, 196, 197, 198, 199,
449   200, 201, 202, 203, 204, 205, 206, 207, 208, 209,
450   210, 211, 212, 213, 214, 215, 216, 217, 218, 219,
451   220, 221, 222, 223, 224, 225, 226, 227, 228, 229,
452   230, 231, 232, 233, 234, 235, 236, 237, 238, 239,
453   240, 241, 242, 243, 244, 245, 246, 247, 248, 249,
454   250, 251, 252, 253, 254, 255,
455   0
456 };
457 
458 
459 /* Get section SECNAME or create one if it doesn't exist.  When creating
460    one, new memory for the name is allocated.  */
461 
462 static asection *
mmo_make_section(bfd * abfd,const char * secname)463 mmo_make_section (bfd *abfd, const char *secname)
464 {
465   asection *sec = bfd_get_section_by_name (abfd, secname);
466 
467   if (sec == NULL)
468     {
469       char *newsecname = strdup (secname);
470 
471       if (newsecname == NULL)
472 	{
473 	  _bfd_error_handler
474 	    /* xgettext:c-format */
475 	    (_("%pB: no core to allocate section name %s"),
476 	     abfd, secname);
477 	  bfd_set_error (bfd_error_system_call);
478 	  return NULL;
479 	}
480       sec = bfd_make_section (abfd, newsecname);
481     }
482 
483   return sec;
484 }
485 
486 /* Nothing to do, but keep as a placeholder if we need it.
487    Note that state that might differ between bfd:s must not be initialized
488    here, nor must it be static.  Add it to tdata information instead.  */
489 
490 static void
mmo_init(void)491 mmo_init (void)
492 {
493   static bool inited = false;
494 
495   if (inited)
496     return;
497   inited = true;
498 }
499 
500 /* Check whether an existing file is an mmo file.  */
501 
502 static bfd_cleanup
mmo_object_p(bfd * abfd)503 mmo_object_p (bfd *abfd)
504 {
505   struct stat statbuf;
506   bfd_byte b[4];
507 
508   mmo_init ();
509 
510   if (bfd_stat (abfd, &statbuf) < 0
511       || bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
512       || bfd_bread (b, 4, abfd) != 4)
513     goto bad_final;
514 
515   /* All mmo files are a multiple of four bytes long.
516      Only recognize version one.  */
517   if ((statbuf.st_size % 4) != 0
518       || b[0] != LOP || b[1] != LOP_PRE || b[2] != 1)
519     goto bad_format;
520 
521   /* Get the last 32-bit word.  */
522   if (bfd_seek (abfd, (file_ptr) statbuf.st_size - 4, SEEK_SET) != 0
523       || bfd_bread (b, 4, abfd) != 4)
524     goto bad_final;
525 
526   /* Check if the file ends in a lop_end lopcode. */
527   if (b[0] != LOP || b[1] != LOP_END || ! mmo_mkobject (abfd))
528     goto bad_format;
529 
530   /* Compute an upper bound on the max symbol length.  Not really
531      important as all of the symbol information can only be 256k.  */
532   abfd->tdata.mmo_data->max_symbol_length = (b[2] * 256 + b[3]) * 4;
533   abfd->tdata.mmo_data->lop_stab_symbol
534     = bfd_malloc (abfd->tdata.mmo_data->max_symbol_length + 1);
535 
536   if (abfd->tdata.mmo_data->lop_stab_symbol == NULL)
537     {
538       _bfd_error_handler
539 	/* xgettext:c-format */
540 	(_("%pB: no core to allocate a symbol %d bytes long"),
541 	 abfd, abfd->tdata.mmo_data->max_symbol_length);
542       goto bad_final;
543     }
544 
545   /* Read in everything.  */
546   if (! mmo_scan (abfd))
547     goto bad_format_free;
548 
549   if (abfd->symcount > 0)
550     abfd->flags |= HAS_SYMS;
551 
552   /* You'll have to tweak this if you want to use this format for other
553      arches (not recommended due to its small-size limitations).  Look at
554      the ELF format for how to make it target-generic.  */
555   if (! bfd_default_set_arch_mach (abfd, bfd_arch_mmix, 0))
556     goto bad_format_free;
557 
558   return _bfd_no_cleanup;
559 
560  bad_format_free:
561   free (abfd->tdata.mmo_data->lop_stab_symbol);
562  bad_format:
563   bfd_set_error (bfd_error_wrong_format);
564  bad_final:
565   return NULL;
566 }
567 
568 /* Set up the mmo tdata information.  */
569 
570 static bool
mmo_mkobject(bfd * abfd)571 mmo_mkobject (bfd *abfd)
572 {
573   mmo_init ();
574 
575   if (abfd->tdata.mmo_data == NULL)
576     {
577       time_t created;
578 
579       /* All fields are zero-initialized, so we don't have to explicitly
580 	 initialize most.  */
581       tdata_type *tdata = (tdata_type *) bfd_zalloc (abfd, sizeof (tdata_type));
582       if (tdata == NULL)
583 	return false;
584 
585       created = time (NULL);
586       bfd_put_32 (abfd, created, tdata->created);
587 
588       abfd->tdata.mmo_data = tdata;
589     }
590 
591   return true;
592 }
593 
594 static bool
mmo_section_has_contents(bfd * abfd ATTRIBUTE_UNUSED,asection * sec,void * p ATTRIBUTE_UNUSED)595 mmo_section_has_contents (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, void *p ATTRIBUTE_UNUSED)
596 {
597   /* The point is to match what --extract-symbols does (well, negated).  */
598   return bfd_section_size (sec) != 0;
599 }
600 
601 /* Find out whether we should omit symbol consistency checks for this
602    bfd and cache the value.
603 
604    This function must only be called when all section contents is
605    known.  However, calculating symbol consistency at the time the
606    private BFD data is initialized is too late for some uses.  */
607 
608 static bool
mmo_ignore_symbol_consistency(bfd * abfd)609 mmo_ignore_symbol_consistency (bfd *abfd)
610 {
611   if (!abfd->tdata.mmo_data->symbol_consistency_override_calculated)
612     {
613       abfd->tdata.mmo_data->ignore_symbol_consistency =
614 	bfd_sections_find_if (abfd, mmo_section_has_contents, NULL) == NULL;
615 
616       abfd->tdata.mmo_data->symbol_consistency_override_calculated = true;
617     }
618 
619   return abfd->tdata.mmo_data->ignore_symbol_consistency;
620 }
621 
622 static bool
mmo_bfd_copy_private_bfd_data(bfd * ibfd,bfd * obfd)623 mmo_bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
624 {
625   if (bfd_get_flavour (ibfd) != bfd_target_mmo_flavour
626       || bfd_get_flavour (obfd) != bfd_target_mmo_flavour)
627     return true;
628 
629   /* Copy the time the copied-from file was created.  If people want the
630      time the file was last *modified*, they have that in the normal file
631      information.  */
632   memcpy (obfd->tdata.mmo_data->created, ibfd->tdata.mmo_data->created,
633 	  sizeof (obfd->tdata.mmo_data->created));
634   return true;
635 }
636 
637 /* Helper functions for mmo_decide_section, used through
638    bfd_map_over_sections.  */
639 
640 static void
mmo_find_sec_w_addr(bfd * abfd ATTRIBUTE_UNUSED,asection * sec,void * p)641 mmo_find_sec_w_addr (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, void *p)
642 {
643   struct mmo_find_sec_info *infop = (struct mmo_find_sec_info *) p;
644   bfd_vma vma = bfd_section_vma (sec);
645 
646   /* Ignore sections that aren't loaded.  */
647   if ((bfd_section_flags (sec) & (SEC_LOAD | SEC_ALLOC))
648       !=  (SEC_LOAD | SEC_ALLOC))
649     return;
650 
651   if (infop->addr >= vma && infop->addr < vma + sec->size)
652     infop->sec = sec;
653 }
654 
655 static void
mmo_find_sec_w_addr_grow(bfd * abfd ATTRIBUTE_UNUSED,asection * sec,void * p)656 mmo_find_sec_w_addr_grow (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, void *p)
657 {
658   struct mmo_find_sec_info *infop = (struct mmo_find_sec_info *) p;
659   bfd_vma vma = bfd_section_vma (sec);
660 
661   /* Ignore sections that aren't loaded.  */
662   if ((bfd_section_flags (sec) & (SEC_LOAD | SEC_ALLOC))
663       !=  (SEC_LOAD | SEC_ALLOC))
664     return;
665 
666   if (infop->addr >= vma && infop->addr < vma + MAX_ARTIFICIAL_SECTION_SIZE)
667     infop->sec = sec;
668 }
669 
670 /* Find a section that corresponds to a VMA.  Automatically create .text
671    or .data and set current section to it, depending on what vma.  If we
672    can't deduce a section, make one up as ".MMIX.sec.N", where N is an
673    increasing number.  */
674 
675 static asection *
mmo_decide_section(bfd * abfd,bfd_vma vma)676 mmo_decide_section (bfd *abfd, bfd_vma vma)
677 {
678   asection *sec = NULL;
679   char sec_name[sizeof (".MMIX.sec.") + 20];
680   struct mmo_find_sec_info info;
681 
682   info.addr = vma;
683   info.sec = NULL;
684 
685   /* First see if there's a section that would match exactly.  */
686   bfd_map_over_sections (abfd, mmo_find_sec_w_addr, &info);
687 
688   if (info.sec != NULL)
689     return info.sec;
690 
691   /* If there's no such section, try and expand one of the existing ones,
692      up to a limit.  Make sure we have .text and .data before we try that;
693      create them corresponding to expected addresses and set flags to make
694      them match the "loaded and with contents" expectation.  */
695   if ((vma >> 56) == 0)
696     {
697       sec = bfd_make_section_old_way (abfd, MMO_TEXT_SECTION_NAME);
698 
699       if (sec == NULL)
700 	return NULL;
701 
702       if (!sec->user_set_vma && !bfd_set_section_vma (sec, vma))
703 	return NULL;
704 
705       if (!bfd_set_section_flags (sec, (bfd_section_flags (sec)
706 					| SEC_CODE | SEC_LOAD | SEC_ALLOC)))
707 	return NULL;
708     }
709   else if ((vma >> 56) == 0x20)
710     {
711       sec = bfd_make_section_old_way (abfd, MMO_DATA_SECTION_NAME);
712 
713       if (sec == NULL)
714 	return NULL;
715 
716       if (!sec->user_set_vma && !bfd_set_section_vma (sec, vma))
717 	return NULL;
718 
719       if (!bfd_set_section_flags (sec, (bfd_section_flags (sec)
720 					| SEC_LOAD | SEC_ALLOC)))
721 	return NULL;
722     }
723 
724   bfd_map_over_sections (abfd, mmo_find_sec_w_addr_grow, &info);
725 
726   if (info.sec != NULL)
727     return info.sec;
728 
729   /* If there's still no suitable section, make a new one.  */
730   sprintf (sec_name, ".MMIX.sec.%d", abfd->tdata.mmo_data->sec_no++);
731   sec = mmo_make_section (abfd, sec_name);
732 
733   if (!sec->user_set_vma && !bfd_set_section_vma (sec, vma))
734     return NULL;
735 
736   if (!bfd_set_section_flags (sec, (bfd_section_flags (sec)
737 				    | SEC_LOAD | SEC_ALLOC)))
738     return NULL;
739   return sec;
740 }
741 
742 /* Xor in a 64-bit value VALUE at VMA.  */
743 
744 static INLINE void
mmo_xore_64(asection * sec,bfd_vma vma,bfd_vma value)745 mmo_xore_64 (asection *sec, bfd_vma vma, bfd_vma value)
746 {
747   bfd_byte *loc = mmo_get_loc (sec, vma, 8);
748   bfd_vma prev = bfd_get_64 (sec->owner, loc);
749 
750   value ^= prev;
751   bfd_put_64 (sec->owner, value, loc);
752 }
753 
754 /* Xor in a 32-bit value VALUE at VMA.  */
755 
756 static INLINE void
mmo_xore_32(asection * sec,bfd_vma vma,unsigned int value)757 mmo_xore_32 (asection *sec, bfd_vma vma, unsigned int value)
758 {
759   bfd_byte *loc = mmo_get_loc (sec, vma, 4);
760   unsigned int prev = bfd_get_32 (sec->owner, loc);
761 
762   value ^= prev;
763   bfd_put_32 (sec->owner, value, loc);
764 }
765 
766 /* Xor in a 16-bit value VALUE at VMA.  */
767 
768 static INLINE void
mmo_xore_16(asection * sec,bfd_vma vma,unsigned int value)769 mmo_xore_16 (asection *sec, bfd_vma vma, unsigned int value)
770 {
771   bfd_byte *loc = mmo_get_loc (sec, vma, 2);
772   unsigned int prev = bfd_get_16 (sec->owner, loc);
773 
774   value ^= prev;
775   bfd_put_16 (sec->owner, value, loc);
776 }
777 
778 /* Write a 32-bit word to output file, no lop_quote generated.  */
779 
780 static INLINE void
mmo_write_tetra_raw(bfd * abfd,unsigned int value)781 mmo_write_tetra_raw (bfd *abfd, unsigned int value)
782 {
783   bfd_byte buf[4];
784 
785   bfd_put_32 (abfd, value, buf);
786 
787   if (bfd_bwrite (buf, 4, abfd) != 4)
788     abfd->tdata.mmo_data->have_error = true;
789 }
790 
791 /* Write a 32-bit word to output file; lop_quote if necessary.  */
792 
793 static INLINE void
mmo_write_tetra(bfd * abfd,unsigned int value)794 mmo_write_tetra (bfd *abfd, unsigned int value)
795 {
796   if (((value >> 24) & 0xff) == LOP)
797     mmo_write_tetra_raw (abfd, LOP_QUOTE_NEXT);
798 
799   mmo_write_tetra_raw (abfd, value);
800 }
801 
802 /* Write a 64-bit word to output file, perhaps with lop_quoting.  */
803 
804 static INLINE void
mmo_write_octa(bfd * abfd,bfd_vma value)805 mmo_write_octa (bfd *abfd, bfd_vma value)
806 {
807   mmo_write_tetra (abfd, (unsigned int) (value >> 32));
808   mmo_write_tetra (abfd, (unsigned int) value);
809 }
810 
811 /* Write a 64-bit word to output file, without lop_quoting.  */
812 
813 static INLINE void
mmo_write_octa_raw(bfd * abfd,bfd_vma value)814 mmo_write_octa_raw (bfd *abfd, bfd_vma value)
815 {
816   mmo_write_tetra_raw (abfd, (unsigned int) (value >> 32));
817   mmo_write_tetra_raw (abfd, (unsigned int) value);
818 }
819 
820 /* Write quoted contents.  Intended to be called multiple times in
821    sequence, followed by a call to mmo_flush_chunk.  */
822 
823 static INLINE bool
mmo_write_chunk(bfd * abfd,const bfd_byte * loc,unsigned int len)824 mmo_write_chunk (bfd *abfd, const bfd_byte *loc, unsigned int len)
825 {
826   bool retval = true;
827   struct mmo_data_struct *mmop = abfd->tdata.mmo_data;
828 
829   /* Fill up a tetra from bytes remaining from a previous chunk.  */
830   if (mmop->byte_no != 0)
831     {
832       while (mmop->byte_no < 4 && len != 0)
833 	{
834 	  mmop->buf[mmop->byte_no++] = *loc++;
835 	  len--;
836 	}
837 
838       if (mmop->byte_no == 4)
839 	{
840 	  mmo_write_tetra (abfd, bfd_get_32 (abfd, mmop->buf));
841 	  mmop->byte_no = 0;
842 	}
843     }
844 
845   while (len >= 4)
846     {
847       if (loc[0] == LOP)
848 	mmo_write_tetra_raw (abfd, LOP_QUOTE_NEXT);
849 
850       retval = (retval
851 		&& ! mmop->have_error
852 		&& 4 == bfd_bwrite (loc, 4, abfd));
853 
854       loc += 4;
855       len -= 4;
856     }
857 
858   if (len)
859     {
860       /* We must have flushed a previous remainder if we get one from
861 	 this chunk too.  */
862       BFD_ASSERT (mmop->byte_no == 0);
863       memcpy (mmop->buf, loc, len);
864       mmop->byte_no = len;
865     }
866 
867   if (! retval)
868     mmop->have_error = true;
869   return retval;
870 }
871 
872 /* Flush remaining bytes, from a previous mmo_write_chunk, zero-padded to
873    4 bytes.  */
874 
875 static INLINE bool
mmo_flush_chunk(bfd * abfd)876 mmo_flush_chunk (bfd *abfd)
877 {
878   if (abfd->tdata.mmo_data->byte_no != 0)
879     {
880       memset (abfd->tdata.mmo_data->buf + abfd->tdata.mmo_data->byte_no,
881 	      0, 4 - abfd->tdata.mmo_data->byte_no);
882       mmo_write_tetra (abfd,
883 		       bfd_get_32 (abfd, abfd->tdata.mmo_data->buf));
884       abfd->tdata.mmo_data->byte_no = 0;
885     }
886 
887   return ! abfd->tdata.mmo_data->have_error;
888 }
889 
890 /* Same, but from a list.  */
891 
892 static INLINE bool
mmo_write_chunk_list(bfd * abfd,mmo_data_list_type * datap)893 mmo_write_chunk_list (bfd *abfd, mmo_data_list_type *datap)
894 {
895   for (; datap != NULL; datap = datap->next)
896     if (! mmo_write_chunk (abfd, datap->data, datap->size))
897       return false;
898 
899   return mmo_flush_chunk (abfd);
900 }
901 
902 /* Write a lop_loc and some contents.  A caller needs to call
903    mmo_flush_chunk after calling this function.  The location is only
904    output if different than *LAST_VMAP, which is updated after this call.  */
905 
906 static bool
mmo_write_loc_chunk(bfd * abfd,bfd_vma vma,const bfd_byte * loc,unsigned int len,bfd_vma * last_vmap)907 mmo_write_loc_chunk (bfd *abfd, bfd_vma vma, const bfd_byte *loc,
908 		     unsigned int len, bfd_vma *last_vmap)
909 {
910   /* Find an initial and trailing section of zero (aligned) tetras; we don't
911      need to write out zeros.  FIXME: When we do this, we should emit
912      section size and address specifiers, else objcopy can't always perform
913      an identity translation.  Only do this if we *don't* have left-over
914      data from a previous write (and will not add any) or else the vma of
915      this chunk is *not* the next address, because then data isn't
916      tetrabyte-aligned and we're concatenating to that left-over data.  */
917 
918   if ((vma & 3) == 0
919       && (abfd->tdata.mmo_data->byte_no == 0 || vma != *last_vmap))
920     {
921       while (len > 4 && bfd_get_32 (abfd, loc) == 0)
922 	{
923 	  vma += 4;
924 	  len -= 4;
925 	  loc += 4;
926 	}
927 
928       if ((len & 3) == 0)
929 	while (len > 4 && bfd_get_32 (abfd, loc + len - 4) == 0)
930 	  len -= 4;
931     }
932 
933   /* Only write out the location if it's different than the one the caller
934      (supposedly) previously handled, accounting for omitted leading zeros.  */
935   if (vma != *last_vmap)
936     {
937       /* We might be in the middle of a sequence.  */
938       mmo_flush_chunk (abfd);
939 
940       /* This should not happen during normal usage, but can presumably
941 	 happen with an erroneous linker-script, so handle gracefully.
942 	 Avoid Knuth-specific terms in the message, such as "tetrabyte".
943 	 Note that this function will get non-4-multiple lengths and
944 	 unaligned vmas but those come in tuples (mostly pairs) and are
945 	 continuous (i.e. the if-condition above false) and they are
946 	 group-wise aligned.  */
947       if ((vma & 3) != 0)
948 	{
949 	  _bfd_error_handler
950 	    /* xgettext:c-format */
951 	    (_("%pB: attempt to emit contents at non-multiple-of-4"
952 	       " address %#" PRIx64 ""),
953 	     abfd, (uint64_t) vma);
954 	  bfd_set_error (bfd_error_bad_value);
955 	  return false;
956 	}
957 
958       /* We always write the location as 64 bits; no use saving bytes
959 	 here.  */
960       mmo_write_tetra_raw (abfd, (LOP << 24) | (LOP_LOC << 16) | 2);
961       mmo_write_octa_raw (abfd, vma);
962     }
963 
964   /* Update to reflect end of this chunk, with trailing zeros omitted.  */
965   *last_vmap = vma + len;
966 
967   return (! abfd->tdata.mmo_data->have_error
968 	  && mmo_write_chunk (abfd, loc, len));
969 }
970 
971 /* Same, but from a list.  */
972 
973 static INLINE bool
mmo_write_loc_chunk_list(bfd * abfd,mmo_data_list_type * datap)974 mmo_write_loc_chunk_list (bfd *abfd, mmo_data_list_type *datap)
975 {
976   /* Get an address different than the address of the first chunk.  */
977   bfd_vma last_vma = datap ? datap->where - 1 : 0;
978 
979   for (; datap != NULL; datap = datap->next)
980     if (! mmo_write_loc_chunk (abfd, datap->where, datap->data, datap->size,
981 			       &last_vma))
982       return false;
983 
984   return mmo_flush_chunk (abfd);
985 }
986 
987 /* Make a .MMIX.spec_data.N section.  */
988 
989 static asection *
mmo_get_generic_spec_data_section(bfd * abfd,int spec_data_number)990 mmo_get_generic_spec_data_section (bfd *abfd, int spec_data_number)
991 {
992   asection *sec;
993   char secname[sizeof (MMIX_OTHER_SPEC_SECTION_PREFIX) + 20]
994     = MMIX_OTHER_SPEC_SECTION_PREFIX;
995 
996   sprintf (secname + strlen (MMIX_OTHER_SPEC_SECTION_PREFIX),
997 	   "%d", spec_data_number);
998 
999   sec = mmo_make_section (abfd, secname);
1000 
1001   return sec;
1002 }
1003 
1004 /* Make a special section for SPEC_DATA_NUMBER.  If it is the one we use
1005    ourselves, parse some of its data to get at the section name.  */
1006 
1007 static asection *
mmo_get_spec_section(bfd * abfd,int spec_data_number)1008 mmo_get_spec_section (bfd *abfd, int spec_data_number)
1009 {
1010   char *secname;
1011   asection *sec;
1012   bfd_byte buf[4];
1013   unsigned int secname_length;
1014   unsigned int i;
1015   bfd_vma section_length;
1016   bfd_vma section_vma;
1017   mmo_data_list_type *loc;
1018   flagword flags;
1019   long orig_pos;
1020 
1021   /* If this isn't the "special" special data, then make a placeholder
1022      section.  */
1023   if (spec_data_number != SPEC_DATA_SECTION)
1024     return mmo_get_generic_spec_data_section (abfd, spec_data_number);
1025 
1026   /* Seek back to this position if there was a format error.  */
1027   orig_pos = bfd_tell (abfd);
1028 
1029   /* Read the length (in 32-bit words).  */
1030   if (bfd_bread (buf, 4, abfd) != 4)
1031     goto format_error;
1032 
1033   if (buf[0] == LOP)
1034     {
1035       if (buf[1] != LOP_QUOTE)
1036 	goto format_error;
1037 
1038       if (bfd_bread (buf, 4, abfd) != 4)
1039 	goto format_error;
1040     }
1041 
1042   /* We don't care to keep the name length accurate.  It's
1043      zero-terminated.  */
1044   secname_length = bfd_get_32 (abfd, buf) * 4;
1045 
1046   /* Check section name length for sanity.  */
1047   if (secname_length > MAX_SECTION_NAME_SIZE)
1048     goto format_error;
1049 
1050   /* This should be free'd regardless if a section is created.  */
1051   secname = bfd_malloc (secname_length + 1);
1052   secname[secname_length] = 0;
1053 
1054   for (i = 0; i < secname_length / 4; i++)
1055     {
1056       if (bfd_bread (secname + i * 4, 4, abfd) != 4)
1057 	goto format_error_free;
1058 
1059       if (secname[i * 4] == (char) LOP)
1060 	{
1061 	  /* A bit of overkill, but we handle char 0x98 in a section name,
1062 	     and recognize misparsing.  */
1063 	  if (secname[i * 4 + 1] != LOP_QUOTE
1064 	      || bfd_bread (secname + i * 4, 4, abfd) != 4)
1065 	    /* Whoops.  We thought this was a name, and now we found a
1066 	       non-lop_quote lopcode before we parsed the whole length of
1067 	       the name.  Signal end-of-file in the same manner.  */
1068 	      goto format_error_free;
1069 	}
1070     }
1071 
1072   /* Get the section flags.  */
1073   if (bfd_bread (buf, 4, abfd) != 4
1074       || (buf[0] == LOP
1075 	  && (buf[1] != LOP_QUOTE || bfd_bread (buf, 4, abfd) != 4)))
1076     goto format_error_free;
1077 
1078   flags = bfd_get_32 (abfd, buf);
1079 
1080   /* Get the section length.  */
1081   if (bfd_bread (buf, 4, abfd) != 4
1082       || (buf[0] == LOP
1083 	  && (buf[1] != LOP_QUOTE || bfd_bread (buf, 4, abfd) != 4)))
1084     goto format_error_free;
1085 
1086   section_length = (bfd_vma) bfd_get_32 (abfd, buf) << 32;
1087 
1088   /* That's the first, high-part.  Now get the low part.  */
1089 
1090   if (bfd_bread (buf, 4, abfd) != 4
1091       || (buf[0] == LOP
1092 	  && (buf[1] != LOP_QUOTE || bfd_bread (buf, 4, abfd) != 4)))
1093     goto format_error_free;
1094 
1095   section_length |= (bfd_vma) bfd_get_32 (abfd, buf);
1096 
1097   /* Check the section length for sanity.  */
1098   if (section_length > MAX_ARTIFICIAL_SECTION_SIZE)
1099     goto format_error_free;
1100 
1101   /* Get the section VMA.  */
1102   if (bfd_bread (buf, 4, abfd) != 4
1103       || (buf[0] == LOP
1104 	  && (buf[1] != LOP_QUOTE || bfd_bread (buf, 4, abfd) != 4)))
1105     goto format_error_free;
1106 
1107   section_vma = (bfd_vma) bfd_get_32 (abfd, buf) << 32;
1108 
1109   /* That's the first, high-part.  Now get the low part.  */
1110   if (bfd_bread (buf, 4, abfd) != 4
1111       || (buf[0] == LOP
1112 	  && (buf[1] != LOP_QUOTE || bfd_bread (buf, 4, abfd) != 4)))
1113     goto format_error_free;
1114 
1115   section_vma |= (bfd_vma) bfd_get_32 (abfd, buf);
1116 
1117   sec = mmo_make_section (abfd, secname);
1118   free (secname);
1119   if (sec == NULL)
1120     goto format_error;
1121 
1122   /* We allocate a buffer here for the advertised size, with head room for
1123      tetrabyte alignment.  */
1124   loc = bfd_zmalloc (section_length + 3
1125 		     + sizeof (struct mmo_data_list_struct));
1126   if (loc == NULL)
1127     goto format_error;
1128 
1129   /* Use a TETRA-rounded size for the allocated buffer; we set the
1130      "visible" section size below.  */
1131   loc->size = (section_length + 3) & ~3;
1132 
1133   /* Add in the section flags we found to those bfd entered during this
1134      process and set the contents.  */
1135   if (!bfd_set_section_flags (sec,
1136 			      (bfd_sec_flags_from_mmo_flags (flags)
1137 			       | bfd_section_flags (sec)
1138 			       | (section_length != 0 ? SEC_HAS_CONTENTS : 0)))
1139       || !bfd_set_section_size (sec, sec->size + section_length)
1140       /* Set VMA only for the first occurrence.  */
1141       || (!sec->user_set_vma && !bfd_set_section_vma (sec, section_vma)))
1142     {
1143       /* If we get an error for any of the calls above, signal more than
1144 	 just a format error for the spec section.  */
1145       return NULL;
1146     }
1147 
1148   loc->next = NULL;
1149   if (mmo_section_data (sec)->tail != NULL)
1150     mmo_section_data (sec)->tail->next = loc;
1151   else
1152     mmo_section_data (sec)->head = loc;
1153   mmo_section_data (sec)->tail = loc;
1154   loc->where = section_vma;
1155 
1156   return sec;
1157 
1158  format_error_free:
1159   free (secname);
1160  format_error:
1161   if (bfd_seek (abfd, orig_pos, SEEK_SET) != 0)
1162     return NULL;
1163 
1164   return mmo_get_generic_spec_data_section (abfd, spec_data_number);
1165 }
1166 
1167 /* Read a byte, but read from file in multiples of 32-bit words.  */
1168 
1169 static bfd_byte
mmo_get_byte(bfd * abfd)1170 mmo_get_byte (bfd *abfd)
1171 {
1172   bfd_byte retval;
1173 
1174   if (abfd->tdata.mmo_data->byte_no == 0)
1175     {
1176       if (! abfd->tdata.mmo_data->have_error
1177 	  && bfd_bread (abfd->tdata.mmo_data->buf, 4, abfd) != 4)
1178 	{
1179 	  abfd->tdata.mmo_data->have_error = true;
1180 
1181 	  /* A value somewhat safe against tripping on some inconsistency
1182 	     when mopping up after this error.  */
1183 	  return 128;
1184 	}
1185     }
1186 
1187   retval = abfd->tdata.mmo_data->buf[abfd->tdata.mmo_data->byte_no];
1188   abfd->tdata.mmo_data->byte_no = (abfd->tdata.mmo_data->byte_no + 1) % 4;
1189 
1190   return retval;
1191 }
1192 
1193 /* Write a byte, in multiples of 32-bit words.  */
1194 
1195 static void
mmo_write_byte(bfd * abfd,bfd_byte value)1196 mmo_write_byte (bfd *abfd, bfd_byte value)
1197 {
1198   abfd->tdata.mmo_data->buf[(abfd->tdata.mmo_data->byte_no++ % 4)] = value;
1199   if ((abfd->tdata.mmo_data->byte_no % 4) == 0)
1200     {
1201       if (! abfd->tdata.mmo_data->have_error
1202 	  && bfd_bwrite (abfd->tdata.mmo_data->buf, 4, abfd) != 4)
1203 	abfd->tdata.mmo_data->have_error = true;
1204     }
1205 }
1206 
1207 /* Create a symbol.  */
1208 
1209 static bool
mmo_create_symbol(bfd * abfd,const char * symname,bfd_vma addr,enum mmo_sym_type sym_type,unsigned int serno)1210 mmo_create_symbol (bfd *abfd, const char *symname, bfd_vma addr, enum
1211 		   mmo_sym_type sym_type, unsigned int serno)
1212 {
1213   struct mmo_symbol *n;
1214 
1215   n = (struct mmo_symbol *) bfd_alloc (abfd, sizeof (struct mmo_symbol));
1216   if (n == NULL)
1217     return false;
1218 
1219   n->name = bfd_alloc (abfd, strlen (symname) + 1);
1220   if (n->name == NULL)
1221     return false;
1222 
1223   strcpy (n->name, symname);
1224 
1225   n->value = addr;
1226   n->sym_type = sym_type;
1227   n->serno = serno;
1228 
1229   if (abfd->tdata.mmo_data->symbols == NULL)
1230     abfd->tdata.mmo_data->symbols = n;
1231   else
1232     abfd->tdata.mmo_data->symtail->next = n;
1233   abfd->tdata.mmo_data->symtail = n;
1234   n->next = NULL;
1235 
1236   ++abfd->symcount;
1237 
1238   /* Check that :Main equals the last octa of the .MMIX.reg_contents
1239      section, as it's the one place we're sure to pass when reading a mmo
1240      object.  For written objects, we do it while setting the symbol
1241      table.  */
1242   if (strcmp (symname, MMIX_START_SYMBOL_NAME) == 0
1243       && bfd_get_start_address (abfd) != addr
1244       && !mmo_ignore_symbol_consistency (abfd))
1245     {
1246       _bfd_error_handler
1247 	(_("%pB: invalid mmo file: initialization value for $255"
1248 	   " is not `Main'\n"),
1249 	 abfd);
1250       bfd_set_error (bfd_error_bad_value);
1251       return false;
1252     }
1253 
1254   return true;
1255 }
1256 
1257 /* Read in symbols.  */
1258 
1259 static bool
mmo_get_symbols(bfd * abfd)1260 mmo_get_symbols (bfd *abfd)
1261 {
1262 /*
1263 INODE
1264 Symbol-table, mmo section mapping, File layout, mmo
1265 SUBSECTION
1266 	Symbol table format
1267 
1268 	From mmixal.w (or really, the generated mmixal.tex) in the
1269 	MMIXware package which also contains the @command{mmix} simulator:
1270 	``Symbols are stored and retrieved by means of a @samp{ternary
1271 	search trie}, following ideas of Bentley and Sedgewick. (See
1272 	ACM--SIAM Symp.@: on Discrete Algorithms @samp{8} (1997), 360--369;
1273 	R.@:Sedgewick, @samp{Algorithms in C} (Reading, Mass.@:
1274 	Addison--Wesley, 1998), @samp{15.4}.)  Each trie node stores a
1275 	character, and there are branches to subtries for the cases where
1276 	a given character is less than, equal to, or greater than the
1277 	character in the trie.  There also is a pointer to a symbol table
1278 	entry if a symbol ends at the current node.''
1279 
1280 	So it's a tree encoded as a stream of bytes.  The stream of bytes
1281 	acts on a single virtual global symbol, adding and removing
1282 	characters and signalling complete symbol points.  Here, we read
1283 	the stream and create symbols at the completion points.
1284 
1285 	First, there's a control byte <<m>>.  If any of the listed bits
1286 	in <<m>> is nonzero, we execute what stands at the right, in
1287 	the listed order:
1288 
1289 | (MMO3_LEFT)
1290 | 0x40 - Traverse left trie.
1291 |        (Read a new command byte and recurse.)
1292 |
1293 | (MMO3_SYMBITS)
1294 | 0x2f - Read the next byte as a character and store it in the
1295 |        current character position; increment character position.
1296 |        Test the bits of <<m>>:
1297 |
1298 |        (MMO3_WCHAR)
1299 |        0x80 - The character is 16-bit (so read another byte,
1300 |               merge into current character.
1301 |
1302 |        (MMO3_TYPEBITS)
1303 |        0xf  - We have a complete symbol; parse the type, value
1304 |               and serial number and do what should be done
1305 |               with a symbol.  The type and length information
1306 |               is in j = (m & 0xf).
1307 |
1308 |               (MMO3_REGQUAL_BITS)
1309 |	        j == 0xf: A register variable.  The following
1310 |                         byte tells which register.
1311 |               j <= 8:   An absolute symbol.  Read j bytes as the
1312 |                         big-endian number the symbol equals.
1313 |                         A j = 2 with two zero bytes denotes an
1314 |                         unknown symbol.
1315 |               j > 8:    As with j <= 8, but add (0x20 << 56)
1316 |                         to the value in the following j - 8
1317 |                         bytes.
1318 |
1319 |               Then comes the serial number, as a variant of
1320 |               uleb128, but better named ubeb128:
1321 |               Read bytes and shift the previous value left 7
1322 |               (multiply by 128).  Add in the new byte, repeat
1323 |               until a byte has bit 7 set.  The serial number
1324 |               is the computed value minus 128.
1325 |
1326 |        (MMO3_MIDDLE)
1327 |        0x20 - Traverse middle trie.  (Read a new command byte
1328 |               and recurse.)  Decrement character position.
1329 |
1330 | (MMO3_RIGHT)
1331 | 0x10 - Traverse right trie.  (Read a new command byte and
1332 |        recurse.)
1333 
1334 	Let's look again at the <<lop_stab>> for the trivial file
1335 	(@pxref{File layout}).
1336 
1337 | 0x980b0000 - lop_stab for ":Main" = 0, serial 1.
1338 | 0x203a4040
1339 | 0x10404020
1340 | 0x4d206120
1341 | 0x69016e00
1342 | 0x81000000
1343 
1344 	This forms the trivial trie (note that the path between ``:'' and
1345 	``M'' is redundant):
1346 
1347 | 203a	   ":"
1348 | 40       /
1349 | 40      /
1350 | 10      \
1351 | 40      /
1352 | 40     /
1353 | 204d  "M"
1354 | 2061  "a"
1355 | 2069  "i"
1356 | 016e  "n" is the last character in a full symbol, and
1357 |       with a value represented in one byte.
1358 | 00    The value is 0.
1359 | 81    The serial number is 1.  */
1360 
1361   bfd_byte m = mmo_get_byte (abfd);
1362 
1363   /* Check first if we have a bad hair day.  */
1364   if (abfd->tdata.mmo_data->have_error)
1365     return false;
1366 
1367   if (m & MMO3_LEFT)
1368     /* Traverse left trie. */
1369     mmo_get_symbols (abfd);
1370 
1371   if (m & MMO3_SYMBITS)
1372     {
1373       bfd_byte c = mmo_get_byte (abfd);
1374       bfd_byte j = m & MMO3_TYPEBITS;
1375       bfd_vma addr = 0;
1376       enum mmo_sym_type sym_type;
1377       unsigned int serno = 0;
1378       bfd_byte k;
1379 
1380       if (m & MMO3_WCHAR)
1381 	{
1382 	  bfd_byte c2 = mmo_get_byte (abfd);
1383 
1384 	  /* A two-byte character.  We can't grok this, but neither can
1385 	     mmotype, for other cases than the second byte being zero.  */
1386 
1387 	  if (c != 0)
1388 	    {
1389 	      abfd->tdata.mmo_data->lop_stab_symbol
1390 		[abfd->tdata.mmo_data->symbol_position] = 0;
1391 
1392 	      _bfd_error_handler
1393 		/* xgettext:c-format */
1394 		(_("%pB: unsupported wide character sequence"
1395 		   " 0x%02X 0x%02X after symbol name starting with `%s'\n"),
1396 		 abfd, c, c2, abfd->tdata.mmo_data->lop_stab_symbol);
1397 	      bfd_set_error (bfd_error_bad_value);
1398 	      abfd->tdata.mmo_data->have_error = true;
1399 	      return false;
1400 	    }
1401 	  else
1402 	    c = c2;
1403 	}
1404 
1405       abfd->tdata.mmo_data->lop_stab_symbol[abfd->tdata.mmo_data->symbol_position++] = c;
1406       abfd->tdata.mmo_data->lop_stab_symbol[abfd->tdata.mmo_data->symbol_position] = 0;
1407 
1408       if (j & MMO3_REGQUAL_BITS)
1409 	{
1410 	  if (j == MMO3_REGQUAL_BITS)
1411 	    {
1412 	      sym_type = mmo_reg_sym;
1413 	      addr = mmo_get_byte (abfd);
1414 	    }
1415 	  else if (j <= 8)
1416 	    {
1417 	      unsigned int i;
1418 
1419 	      for (i = 0; i < j; i++)
1420 		addr = (addr << 8) + mmo_get_byte (abfd);
1421 
1422 	      if (addr == 0 && j == MMO3_UNDEF)
1423 		sym_type = mmo_undef_sym;
1424 	      else
1425 		sym_type = mmo_abs_sym;
1426 	    }
1427 	  else
1428 	    {
1429 	      unsigned int i;
1430 
1431 	      for (i = MMO3_DATA; i < j; i++)
1432 		addr = (addr << 8) + mmo_get_byte (abfd);
1433 
1434 	      addr += (bfd_vma) 0x20 << 56;
1435 	      sym_type = mmo_data_sym;
1436 	    }
1437 
1438 	  /* Get the serial number.  */
1439 	  do
1440 	    {
1441 	      k = mmo_get_byte (abfd);
1442 	      serno = (serno << 7) + k;
1443 	    }
1444 	  while (k < 128);
1445 	  serno -= 128;
1446 
1447 	  /* Got it.  Now enter it.  Skip a leading ":".  */
1448 	  if (! abfd->tdata.mmo_data->have_error
1449 	      && ! mmo_create_symbol (abfd,
1450 				      abfd->tdata.mmo_data->lop_stab_symbol
1451 				      + 1,
1452 				      addr, sym_type, serno))
1453 	    abfd->tdata.mmo_data->have_error = true;
1454 	}
1455 
1456       if (m & MMO3_MIDDLE)
1457 	/* Traverse middle trie. */
1458 	mmo_get_symbols (abfd);
1459 
1460       abfd->tdata.mmo_data->symbol_position--;
1461     }
1462 
1463   if (m & MMO3_RIGHT)
1464     /* Traverse right trie.  */
1465     mmo_get_symbols (abfd);
1466 
1467   return ! abfd->tdata.mmo_data->have_error;
1468 }
1469 
1470 /* Get the location of memory area [VMA..VMA + SIZE - 1], which we think
1471    is in section SEC.  Adjust and reallocate zero-initialized contents.
1472    If there's new contents, allocate to the next multiple of
1473    MMO_SEC_CONTENTS_CHUNK_SIZE.  */
1474 
1475 static INLINE bfd_byte *
mmo_get_loc(asection * sec,bfd_vma vma,int size)1476 mmo_get_loc (asection *sec, bfd_vma vma, int size)
1477 {
1478   bfd_size_type allocated_size;
1479   struct mmo_section_data_struct *sdatap = mmo_section_data (sec);
1480   struct mmo_data_list_struct *datap = sdatap->head;
1481   struct mmo_data_list_struct *entry;
1482 
1483   /* First search the list to see if we have the requested chunk in one
1484      piece, or perhaps if we have a suitable chunk with room to fit.  */
1485   for (; datap != NULL; datap = datap->next)
1486     {
1487       if (datap->where <= vma
1488 	  && datap->where + datap->size >= vma + size)
1489 	return datap->data + vma - datap->where;
1490       else if (datap->where <= vma
1491 	       && datap->where + datap->allocated_size >= vma + size
1492 	       /* Only munch on the "allocated size" if it does not
1493 		  overlap the next chunk.  */
1494 	       && (datap->next == NULL || datap->next->where >= vma + size))
1495 	{
1496 	  /* There was room allocated, but the size wasn't set to include
1497 	     it.  Do that now.  */
1498 	  datap->size += (vma + size) - (datap->where + datap->size);
1499 
1500 	  /* Update the section size.  This happens only if we update the
1501 	     32-bit-aligned chunk size.  Callers that have
1502 	     non-32-bit-aligned sections should do all allocation and
1503 	     size-setting by themselves or at least set the section size
1504 	     after the last allocating call to this function.  */
1505 	  if (vma + size > sec->vma + sec->size)
1506 	    sec->size += (vma + size) - (sec->vma + sec->size);
1507 
1508 	  return datap->data + vma - datap->where;
1509 	}
1510     }
1511 
1512   /* Not found; allocate a new block.  First check in case we get a
1513      request for a size split up over several blocks; we'll have to return
1514      NULL for those cases, requesting the caller to split up the request.
1515      Requests with an address aligned on MMO_SEC_CONTENTS_CHUNK_SIZE bytes and
1516      for no more than MMO_SEC_CONTENTS_CHUNK_SIZE will always get resolved.  */
1517 
1518   for (datap = sdatap->head; datap != NULL; datap = datap->next)
1519     if ((datap->where <= vma && datap->where + datap->size > vma)
1520 	|| (datap->where < vma + size
1521 	    && datap->where + datap->size >= vma + size))
1522       return NULL;
1523 
1524   allocated_size
1525     = (size + MMO_SEC_CONTENTS_CHUNK_SIZE - 1) & ~(MMO_SEC_CONTENTS_CHUNK_SIZE - 1);
1526   entry = (mmo_data_list_type *)
1527     bfd_zalloc (sec->owner, sizeof (mmo_data_list_type) + allocated_size);
1528   if (entry == NULL)
1529     return NULL;
1530   entry->where = vma;
1531   entry->size = size;
1532   entry->allocated_size = allocated_size;
1533 
1534   datap = sdatap->head;
1535 
1536   /* Sort the records by address.  Optimize for the common case of adding
1537      a record to the end of the list.  */
1538   if (sdatap->tail != NULL && entry->where >= sdatap->tail->where)
1539     {
1540       sdatap->tail->next = entry;
1541       entry->next = NULL;
1542       sdatap->tail = entry;
1543     }
1544   else
1545     {
1546       mmo_data_list_type **look;
1547       for (look = &sdatap->head;
1548 	   *look != NULL && (*look)->where < entry->where;
1549 	   look = &(*look)->next)
1550 	;
1551       entry->next = *look;
1552       *look = entry;
1553       if (entry->next == NULL)
1554 	{
1555 	  sdatap->tail = entry;
1556 
1557 	  /* We get here for the first time (at other times too) for this
1558 	     section.  Say we have contents.  */
1559 	  if (!bfd_set_section_flags (sec, (bfd_section_flags (sec)
1560 					    | SEC_HAS_CONTENTS)))
1561 	    return NULL;
1562 	}
1563     }
1564 
1565   /* Update the section size.  This happens only when we add contents and
1566      re-size as we go.  The section size will then be aligned to 32 bits.  */
1567   if (vma + size > sec->vma + sec->size)
1568     sec->size += (vma + size) - (sec->vma + sec->size);
1569   return entry->data;
1570 }
1571 
1572 /* Set sizes once we've read in all sections.  */
1573 
1574 static void
mmo_map_set_sizes(bfd * abfd ATTRIBUTE_UNUSED,asection * sec,void * ignored ATTRIBUTE_UNUSED)1575 mmo_map_set_sizes (bfd *abfd ATTRIBUTE_UNUSED, asection *sec,
1576 		   void *ignored ATTRIBUTE_UNUSED)
1577 {
1578   sec->lma = sec->vma;
1579 }
1580 
1581 /* Read the mmo file and turn it into sections.  */
1582 
1583 static bool
mmo_scan(bfd * abfd)1584 mmo_scan (bfd *abfd)
1585 {
1586   unsigned int i;
1587   unsigned int lineno = 1;
1588   bool error = false;
1589   bfd_vma vma = 0;
1590   asection *sec = NULL;
1591   asection *non_spec_sec = NULL;
1592   bfd_vma non_spec_vma = 0;
1593   bfd_size_type nbytes_read = 0;
1594   /* Buffer with room to read a 64-bit value.  */
1595   bfd_byte buf[8];
1596   file_ptr stab_loc = -1;
1597   char *file_names[256];
1598 
1599   abfd->symcount = 0;
1600   memset (file_names, 0, sizeof (file_names));
1601 
1602   if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
1603     goto error_return;
1604 
1605   while ((nbytes_read = bfd_bread (buf, 4, abfd)) == 4)
1606     {
1607       if (buf[0] == LOP)
1608 	{
1609 	  unsigned int y = bfd_get_8 (abfd, buf + 2);
1610 	  unsigned int z = bfd_get_8 (abfd, buf + 3);
1611 
1612 	  /* Change back to the original section for lopcodes other
1613 	     than LOP_QUOTE that comes after a LOP_SPEC.  */
1614 	  if ((buf[1] != LOP_QUOTE || y != 0 || z != 1)
1615 	      && non_spec_sec != NULL)
1616 	    {
1617 	      sec = non_spec_sec;
1618 	      vma = non_spec_vma;
1619 	      non_spec_sec = NULL;
1620 	    }
1621 
1622 	  switch (buf[1])
1623 	    {
1624 	    default:
1625 	      _bfd_error_handler
1626 		/* xgettext:c-format */
1627 		(_("%pB: invalid mmo file: unsupported lopcode `%d'\n"),
1628 		 abfd, buf[1]);
1629 	      bfd_set_error (bfd_error_bad_value);
1630 	      goto error_return;
1631 
1632 	    case LOP_QUOTE:
1633 	      /* Quote the next 32-bit word.  */
1634 	      if (y != 0 || z != 1)
1635 		{
1636 		  _bfd_error_handler
1637 		    /* xgettext:c-format */
1638 		    (_("%pB: invalid mmo file: expected YZ = 1"
1639 		       " got YZ = %d for lop_quote\n"),
1640 		     abfd, y*256+z);
1641 		  bfd_set_error (bfd_error_bad_value);
1642 		  goto error_return;
1643 		}
1644 	      if (bfd_bread (buf, 4, abfd) != 4)
1645 		goto error_return;
1646 
1647 	      vma &= ~3;
1648 	      if (sec == NULL)
1649 		sec = bfd_make_section_old_way (abfd, MMO_TEXT_SECTION_NAME);
1650 	      mmo_xore_32 (sec, vma, bfd_get_32 (abfd, buf));
1651 	      vma += 4;
1652 	      lineno++;
1653 	      break;
1654 
1655 	    case LOP_LOC:
1656 	      /* Set vma (and section).  */
1657 	      vma = (bfd_vma) y << 56;
1658 	      if (z == 1)
1659 		{
1660 		  /* Get a 32-bit value.  */
1661 		  if (bfd_bread (buf, 4, abfd) != 4)
1662 		    goto error_return;
1663 
1664 		  vma += bfd_get_32 (abfd, buf);
1665 		}
1666 	      else if (z == 2)
1667 		{
1668 		  /* Get a 64-bit value.  */
1669 		  if (bfd_bread (buf, 8, abfd) != 8)
1670 		    goto error_return;
1671 
1672 		  vma += bfd_get_64 (abfd, buf);
1673 		}
1674 	      else
1675 		{
1676 		  _bfd_error_handler
1677 		    /* xgettext:c-format */
1678 		    (_("%pB: invalid mmo file: expected z = 1 or z = 2,"
1679 		       " got z = %d for lop_loc\n"),
1680 		     abfd, z);
1681 		  bfd_set_error (bfd_error_bad_value);
1682 		  goto error_return;
1683 		}
1684 
1685 	      /* When we decide which section the data goes into, we might
1686 		 create the section.  If that happens, make sure the VMA at
1687 		 creation time is tetra-aligned.  */
1688 	      sec = mmo_decide_section (abfd, vma & ~3);
1689 	      if (sec == NULL)
1690 		goto error_return;
1691 	      break;
1692 
1693 	    case LOP_SKIP:
1694 	      /* Move forward within the same section.  */
1695 	      vma += y * 256 + z;
1696 
1697 	      sec = mmo_decide_section (abfd, vma);
1698 	      if (sec == NULL)
1699 		goto error_return;
1700 	      break;
1701 
1702 	    case LOP_FIXO:
1703 	      /* A fixup: Store the current vma somewhere.  Position using
1704 		 same format as LOP_LOC.  */
1705 	      {
1706 		bfd_vma p = (bfd_vma) y << 56;
1707 		asection *fixosec;
1708 
1709 		if (z == 1)
1710 		  {
1711 		    /* Get a 32-bit value.  */
1712 		    if (bfd_bread (buf, 4, abfd) != 4)
1713 		      goto error_return;
1714 
1715 		    p += bfd_get_32 (abfd, buf);
1716 		  }
1717 		else if (z == 2)
1718 		  {
1719 		    /* Get a 64-bit value.  */
1720 		    if (bfd_bread (buf, 8, abfd) != 8)
1721 		      goto error_return;
1722 
1723 		    p += bfd_get_64 (abfd, buf);
1724 		  }
1725 		else
1726 		  {
1727 		    _bfd_error_handler
1728 		      /* xgettext:c-format */
1729 		      (_("%pB: invalid mmo file: expected z = 1 or z = 2,"
1730 			 " got z = %d for lop_fixo\n"),
1731 		       abfd, z);
1732 		    bfd_set_error (bfd_error_bad_value);
1733 		    goto error_return;
1734 		  }
1735 
1736 		/* The section where we store this address might be a
1737 		   different one than the current section.  */
1738 		fixosec = mmo_decide_section (abfd, p);
1739 		if (fixosec == NULL)
1740 		  goto error_return;
1741 		mmo_xore_64 (fixosec, p, vma);
1742 	      }
1743 	    break;
1744 
1745 	    case LOP_FIXR:
1746 	      /* A fixup: Store YZ of this lopcode into YZ at vma - 4 * yz.  */
1747 	      {
1748 		unsigned int yz = (y * 256 + z);
1749 		bfd_vma p = vma + 2 - 4 * yz;
1750 		asection *fixrsec = mmo_decide_section (abfd, p);
1751 		if (fixrsec == NULL)
1752 		  goto error_return;
1753 		mmo_xore_16 (fixrsec, p, yz);
1754 	      }
1755 	    break;
1756 
1757 	    case LOP_FIXRX:
1758 	      /* A fixup, similar to lop_fixr, but taking larger numbers
1759 		 and can change branches into the opposite direction
1760 		 (gasp!).  */
1761 	      {
1762 		bfd_vma delta;
1763 		bfd_vma p;
1764 		asection *fixrsec;
1765 
1766 		if (y != 0)
1767 		  {
1768 		    _bfd_error_handler
1769 		      /* xgettext:c-format */
1770 		      (_("%pB: invalid mmo file: expected y = 0,"
1771 			 " got y = %d for lop_fixrx\n"),
1772 		       abfd, y);
1773 		    bfd_set_error (bfd_error_bad_value);
1774 		    goto error_return;
1775 		  }
1776 
1777 		if (z != 16 && z != 24)
1778 		  {
1779 		    _bfd_error_handler
1780 		      /* xgettext:c-format */
1781 		      (_("%pB: invalid mmo file: expected z = 16 or z = 24,"
1782 			 " got z = %d for lop_fixrx\n"),
1783 		       abfd, z);
1784 		    bfd_set_error (bfd_error_bad_value);
1785 		    goto error_return;
1786 		  }
1787 
1788 		/* Get the next 32-bit value.  */
1789 		if (bfd_bread (buf, 4, abfd) != 4)
1790 		  goto error_return;
1791 
1792 		delta = bfd_get_32 (abfd, buf);
1793 
1794 		/* Do an, ehm, involved calculation for the location of
1795 		   the fixup.  See mmixal documentation for a verbose
1796 		   explanation.  We follow it verbosely here for the
1797 		   readers delight.  */
1798 		if (buf[0] == 0)
1799 		  p = vma - 4 * delta;
1800 		else if (buf[0] == 1)
1801 		  p = vma - 4 * ((delta & 0xffffff) - (1 << z));
1802 		else
1803 		  {
1804 		    _bfd_error_handler
1805 		      /* xgettext:c-format */
1806 		      (_("%pB: invalid mmo file: leading byte of operand word"
1807 			 " must be 0 or 1, got %d for lop_fixrx\n"),
1808 		       abfd, buf[0]);
1809 		    bfd_set_error (bfd_error_bad_value);
1810 		    goto error_return;
1811 		  }
1812 
1813 		fixrsec = mmo_decide_section (abfd, vma);
1814 		if (fixrsec == NULL)
1815 		  goto error_return;
1816 		mmo_xore_32 (fixrsec, p, delta);
1817 	      }
1818 	    break;
1819 
1820 	    case LOP_FILE:
1821 	      /* Set current file and perhaps the file name.  Reset line
1822 		 number.  */
1823 	      if (z != 0)
1824 		{
1825 		  char *fname = bfd_malloc (z * 4 + 1);
1826 
1827 		  if (fname == NULL)
1828 		    {
1829 		      _bfd_error_handler
1830 			/* xgettext:c-format */
1831 			(_("%pB: cannot allocate file name for file number %d,"
1832 			   " %d bytes\n"),
1833 			 abfd, y, z * 4 + 1);
1834 		      bfd_set_error (bfd_error_system_call);
1835 		      goto error_return;
1836 		    }
1837 
1838 		  fname[z * 4] = 0;
1839 
1840 		  for (i = 0; i < z; i++)
1841 		    {
1842 		      if (bfd_bread (fname + i * 4, 4, abfd) != 4)
1843 			{
1844 			  free (fname);
1845 			  goto error_return;
1846 			}
1847 		    }
1848 
1849 		  if (file_names[y] != NULL)
1850 		    {
1851 		      _bfd_error_handler
1852 			/* xgettext:c-format */
1853 			(_("%pB: invalid mmo file: file number %d `%s',"
1854 			   " was already entered as `%s'\n"),
1855 			 abfd, y, fname, file_names[y]);
1856 		      bfd_set_error (bfd_error_bad_value);
1857 		      goto error_return;
1858 		    }
1859 
1860 		  file_names[y] = fname;
1861 		}
1862 
1863 	      if (file_names[y] == NULL)
1864 		{
1865 		  _bfd_error_handler
1866 		    /* xgettext:c-format */
1867 		    (_("%pB: invalid mmo file: file name for number %d"
1868 		       " was not specified before use\n"),
1869 		     abfd, y);
1870 		  bfd_set_error (bfd_error_bad_value);
1871 		  goto error_return;
1872 		}
1873 
1874 	      lineno = 0;
1875 	      break;
1876 
1877 	    case LOP_LINE:
1878 	      /* Set line number.  */
1879 	      lineno = y * 256 + z;
1880 	      /* FIXME: Create a sequence of mmo-specific line number
1881 		 entries for each section, then translate into canonical
1882 		 format.  */
1883 	      break;
1884 
1885 	    case LOP_SPEC:
1886 	      /* Special data follows until the next non-lop_quote
1887 		 lopcode.  */
1888 	      non_spec_sec = sec;
1889 	      non_spec_vma = vma;
1890 	      sec = mmo_get_spec_section (abfd, y * 256 + z);
1891 	      if (sec == NULL)
1892 		goto error_return;
1893 
1894 	      vma = sec->vma;
1895 	      break;
1896 
1897 	    case LOP_PRE:
1898 	      {
1899 		/* We ignore header information, except we read in the
1900 		   creation time from the first 32-bit word with the time
1901 		   in seconds since era.  */
1902 		if (z >= 1
1903 		    && bfd_bread (abfd->tdata.mmo_data->created, 4,
1904 				 abfd) != 4)
1905 		  goto error_return;
1906 
1907 		for (i = 1; i < z; i++)
1908 		  if (bfd_bread (buf, 4, abfd) != 4)
1909 		    goto error_return;
1910 	      }
1911 	      break;
1912 
1913 	    case LOP_POST:
1914 	      /* This tells of the contents of registers $Z..$255 at
1915 		 startup.  We make a section out of it, with VMA = Z * 8,
1916 		 but only if Z != 255 or the contents is non-zero.  */
1917 	      {
1918 		asection *rsec;
1919 		bfd_byte *loc;
1920 		bfd_vma first_octa;
1921 		bfd_vma startaddr_octa;
1922 
1923 		/* Read first octaword outside loop to simplify logic when
1924 		   excluding the Z == 255, octa == 0 case.  */
1925 		if (bfd_bread (buf, 8, abfd) != 8)
1926 		  goto error_return;
1927 
1928 		first_octa = bfd_get_64 (abfd, buf);
1929 
1930 		/* Don't emit contents for the trivial case which is
1931 		   always present; $255 pointing to Main.  */
1932 		if (z != 255)
1933 		  {
1934 		    rsec
1935 		      = bfd_make_section_old_way (abfd,
1936 						  MMIX_REG_CONTENTS_SECTION_NAME);
1937 		    rsec->flags |= SEC_LINKER_CREATED;
1938 		    rsec->vma = z * 8;
1939 		    loc = mmo_get_loc (rsec, z * 8, (255 - z) * 8);
1940 		    bfd_put_64 (abfd, first_octa, loc);
1941 
1942 		    for (i = z + 1; i < 255; i++)
1943 		      {
1944 			if (bfd_bread (loc + (i - z) * 8, 8, abfd) != 8)
1945 			  goto error_return;
1946 		      }
1947 
1948 		    /* Read out the last octabyte, and use it to set the
1949 		       start address.  */
1950 		    if (bfd_bread (buf, 8, abfd) != 8)
1951 		      goto error_return;
1952 
1953 		    startaddr_octa = bfd_get_64 (abfd, buf);
1954 		  }
1955 		else
1956 		  startaddr_octa = first_octa;
1957 
1958 		if (! bfd_set_start_address (abfd, startaddr_octa))
1959 		  {
1960 		    /* Currently this can't fail, but this should handle
1961 		       future failures.  */
1962 		    bfd_set_error (bfd_error_bad_value);
1963 		    goto error_return;
1964 		  }
1965 	      }
1966 	      break;
1967 
1968 	    case LOP_STAB:
1969 	      /* We read in the symbols now, not later.  */
1970 	      if (y != 0 || z != 0)
1971 		{
1972 		  _bfd_error_handler
1973 		    /* xgettext:c-format */
1974 		    (_("%pB: invalid mmo file: fields y and z of lop_stab"
1975 		       " non-zero, y: %d, z: %d\n"),
1976 		     abfd, y, z);
1977 		  bfd_set_error (bfd_error_bad_value);
1978 		  goto error_return;
1979 		}
1980 
1981 	      /* Save the location, so we can check that YZ in the LOP_END
1982 		 is correct.  */
1983 	      stab_loc = bfd_tell (abfd);
1984 
1985 	      /* It's not said that an MMO can be without symbols (though
1986 		 mmixal will refuse to assemble files without Main), but
1987 		 it seems it would still be a valid mmo-file, so allow it.
1988 		 We detect the absence of a symbol area in that the upper
1989 		 limit is computed (from the lop_end YZ field) as 0.
1990 		 Don't call mmo_get_symbols; it can only detect the end of
1991 		 a valid symbol trie, not the absence of one.  */
1992 	      if (abfd->tdata.mmo_data->max_symbol_length != 0
1993 		  && ! mmo_get_symbols (abfd))
1994 		goto error_return;
1995 	      break;
1996 
1997 	    case LOP_END:
1998 	      {
1999 		/* This must be the last 32-bit word in an mmo file.
2000 		   Let's find out.  */
2001 		struct stat statbuf;
2002 		file_ptr curpos = bfd_tell (abfd);
2003 
2004 		if (bfd_stat (abfd, &statbuf) < 0)
2005 		  goto error_return;
2006 
2007 		if (statbuf.st_size != curpos)
2008 		  {
2009 		    _bfd_error_handler
2010 		      /* xgettext:c-format */
2011 		      (_("%pB: invalid mmo file: lop_end not last item in"
2012 			 " file\n"),
2013 		       abfd);
2014 		    bfd_set_error (bfd_error_bad_value);
2015 		    goto error_return;
2016 		  }
2017 
2018 		/* Check that the YZ field is right.  Subtract the size of
2019 		   this LOP_END in the calculation; YZ does not include
2020 		   it.  */
2021 		if ((long) (y * 256 + z) * 4 != (curpos - stab_loc) - 4)
2022 		  {
2023 		    _bfd_error_handler
2024 		      /* xgettext:c-format */
2025 		      (_("%pB: invalid mmo file: YZ of lop_end (%ld)"
2026 			 " not equal to the number of tetras to the preceding"
2027 			 " lop_stab (%ld)\n"),
2028 		       abfd, (long) (y * 256 + z),
2029 		       (long) (curpos - stab_loc - 4)/4);
2030 		    bfd_set_error (bfd_error_bad_value);
2031 		    goto error_return;
2032 		  }
2033 
2034 		bfd_map_over_sections (abfd, mmo_map_set_sizes, NULL);
2035 		goto done;
2036 	      }
2037 	    }
2038 	}
2039       else
2040 	{
2041 	  /* This wasn't a lopcode, so store it in the current section.  */
2042 	  if (sec == NULL)
2043 	    sec = bfd_make_section_old_way (abfd, MMO_TEXT_SECTION_NAME);
2044 	  mmo_xore_32 (sec, vma & ~3, bfd_get_32 (abfd, buf));
2045 	  vma += 4;
2046 	  vma &= ~3;
2047 	  lineno++;
2048 	}
2049     }
2050 
2051   /* We know this file is a multiple of four bytes (checked in
2052      mmo_object_p), so if we got something other than 0, this was a bad
2053      file (although it's more likely we'll get 0 in that case too).
2054      If we got end-of-file, then there was no lop_stab, so the file has
2055      invalid format.  */
2056 
2057   if (nbytes_read != 0)
2058     bfd_set_error (bfd_error_system_call);
2059   else
2060     bfd_set_error (bfd_error_bad_value);
2061 
2062  error_return:
2063   error = true;
2064  done:
2065   /* Mark the .text and .data section with their normal attribute if they
2066      contain anything.  This is not redundant wrt. mmo_decide_section,
2067      since that code might never execute, and conversely the alloc+code
2068      section flags must be set then.  */
2069   sec = bfd_get_section_by_name (abfd, MMO_TEXT_SECTION_NAME);
2070   if (sec != NULL
2071       && (bfd_section_flags (sec) & SEC_HAS_CONTENTS)
2072       && !bfd_set_section_flags (sec, (bfd_section_flags (sec)
2073 				       | SEC_ALLOC | SEC_LOAD | SEC_CODE)))
2074     error = true;
2075 
2076   sec = bfd_get_section_by_name (abfd, MMO_DATA_SECTION_NAME);
2077   if (sec != NULL
2078       && (bfd_section_flags (sec) & SEC_HAS_CONTENTS)
2079       && !bfd_set_section_flags (sec, (bfd_section_flags (sec)
2080 				       | SEC_ALLOC | SEC_LOAD | SEC_DATA)))
2081     error = true;
2082 
2083   /* Free whatever resources we took.  */
2084   for (i = 0; i < sizeof (file_names) / sizeof (file_names[0]); i++)
2085     free (file_names[i]);
2086   return ! error;
2087 }
2088 
2089 /* A hook to set up object file dependent section information.  For mmo,
2090    we point out the shape of allocated section contents.  */
2091 
2092 static bool
mmo_new_section_hook(bfd * abfd,asection * newsect)2093 mmo_new_section_hook (bfd *abfd, asection *newsect)
2094 {
2095   if (!newsect->used_by_bfd)
2096     {
2097       /* We zero-fill all fields and assume NULL is represented by an all
2098 	 zero-bit pattern.  */
2099       newsect->used_by_bfd
2100 	= bfd_zalloc (abfd, sizeof (struct mmo_section_data_struct));
2101       if (!newsect->used_by_bfd)
2102 	return false;
2103     }
2104 
2105   /* Always align to at least 32-bit words.  */
2106   newsect->alignment_power = 2;
2107   return _bfd_generic_new_section_hook (abfd, newsect);
2108 }
2109 
2110 /* We already have section contents loaded for sections that have
2111    contents.  */
2112 
2113 static bool
mmo_get_section_contents(bfd * abfd ATTRIBUTE_UNUSED,asection * sec,void * location,file_ptr offset,bfd_size_type bytes_to_do)2114 mmo_get_section_contents (bfd *abfd ATTRIBUTE_UNUSED,
2115 			  asection *sec,
2116 			  void * location,
2117 			  file_ptr offset,
2118 			  bfd_size_type bytes_to_do)
2119 {
2120   /* Iterate over diminishing chunk sizes, copying contents, like
2121      mmo_set_section_contents.  */
2122   while (bytes_to_do)
2123     {
2124       /* A minor song-and-dance to make sure we're not bitten by the
2125 	 distant possibility of the cast from bfd_vma to int making the
2126 	 chunk zero-sized.  */
2127       int chunk_size
2128 	= (int) bytes_to_do != 0 ? bytes_to_do : MMO_SEC_CONTENTS_CHUNK_SIZE;
2129       bfd_byte *loc;
2130 
2131       do
2132 	loc = mmo_get_loc (sec, sec->vma + offset, chunk_size);
2133       while (loc == NULL && (chunk_size /= 2) != 0);
2134 
2135       if (chunk_size == 0)
2136 	return false;
2137 
2138       memcpy (location, loc, chunk_size);
2139 
2140       location = (bfd_byte *) location + chunk_size;
2141       bytes_to_do -= chunk_size;
2142       offset += chunk_size;
2143     }
2144   return true;
2145 }
2146 
2147 /* Return the amount of memory needed to read the symbol table.  */
2148 
2149 static long
mmo_get_symtab_upper_bound(bfd * abfd)2150 mmo_get_symtab_upper_bound (bfd *abfd)
2151 {
2152   return (abfd->symcount + 1) * sizeof (asymbol *);
2153 }
2154 
2155 /* Sort mmo symbols by serial number.  */
2156 
2157 static int
mmo_sort_mmo_symbols(const void * arg1,const void * arg2)2158 mmo_sort_mmo_symbols (const void *arg1, const void *arg2)
2159 {
2160   const struct mmo_symbol *sym1 = *(const struct mmo_symbol **) arg1;
2161   const struct mmo_symbol *sym2 = *(const struct mmo_symbol **) arg2;
2162 
2163   /* Sort by serial number first.  */
2164   if (sym1->serno < sym2->serno)
2165     return -1;
2166   else if (sym1->serno > sym2->serno)
2167     return 1;
2168 
2169   /* Then sort by address of the table entries.  */
2170   return ((const char *) arg1 - (const char *) arg2);
2171 }
2172 
2173 /* Translate the symbol table.  */
2174 
2175 static long
mmo_canonicalize_symtab(bfd * abfd,asymbol ** alocation)2176 mmo_canonicalize_symtab (bfd *abfd, asymbol **alocation)
2177 {
2178   unsigned int symcount = bfd_get_symcount (abfd);
2179   asymbol *csymbols;
2180   unsigned int i;
2181 
2182   csymbols = abfd->tdata.mmo_data->csymbols;
2183   if (csymbols == NULL && symcount != 0)
2184     {
2185       asymbol *c;
2186       struct mmo_symbol *s;
2187       struct mmo_symbol **msp;
2188 
2189       /* First we store the symbols into the table we'll return, then we
2190 	 qsort it on the serial number, with secondary on the address of
2191 	 the symbol, to preserve order if there would be non-unique serial
2192 	 numbers.  */
2193       for (s = abfd->tdata.mmo_data->symbols,
2194 	     msp = (struct mmo_symbol **) alocation;
2195 	   s != NULL;
2196 	   s = s->next, ++msp)
2197 	*msp = s;
2198 
2199       *msp = NULL;
2200 
2201       qsort (alocation, symcount, sizeof (struct mmo_symbol *),
2202 	     mmo_sort_mmo_symbols);
2203 
2204       csymbols = (asymbol *) bfd_alloc (abfd, symcount * sizeof (asymbol));
2205       if (csymbols == NULL)
2206 	return -1;
2207       abfd->tdata.mmo_data->csymbols = csymbols;
2208 
2209       for (msp = (struct mmo_symbol **) alocation, c = csymbols;
2210 	   *msp != NULL;
2211 	   msp++, ++c)
2212 	{
2213 	  s = *msp;
2214 	  c->the_bfd = abfd;
2215 	  c->name = s->name;
2216 	  c->value = s->value;
2217 	  c->flags = BSF_GLOBAL;
2218 
2219 	  if (s->sym_type == mmo_data_sym)
2220 	    {
2221 	      c->section
2222 		= bfd_get_section_by_name (abfd, MMO_DATA_SECTION_NAME);
2223 
2224 	      if (c->section == NULL)
2225 		c->section = bfd_abs_section_ptr;
2226 	      else
2227 		c->value -= c->section->vma;
2228 	    }
2229 	  else if (s->sym_type == mmo_undef_sym)
2230 	    c->section = bfd_und_section_ptr;
2231 	  else if (s->sym_type == mmo_reg_sym)
2232 	    {
2233 	      c->section
2234 		= bfd_make_section_old_way (abfd, MMIX_REG_SECTION_NAME);
2235 	      c->section->flags |= SEC_LINKER_CREATED;
2236 	    }
2237 	  else
2238 	    {
2239 	      asection *textsec
2240 		= bfd_get_section_by_name (abfd, MMO_TEXT_SECTION_NAME);
2241 	      asection *datasec;
2242 
2243 	      if (textsec != NULL
2244 		  && c->value >= textsec->vma
2245 		  && c->value <= textsec->vma + textsec->size)
2246 		{
2247 		  c->section = textsec;
2248 		  c->value -= c->section->vma;
2249 		}
2250 	      /* In mmo, symbol types depend on the VMA.  Therefore, if
2251 		 the data section isn't within the usual bounds, its
2252 		 symbols are marked as absolute.  Correct that.  This
2253 		 means we can't have absolute symbols with values matching
2254 		 data section addresses, but we also can't have with
2255 		 absolute symbols with values matching text section
2256 		 addresses.  For such needs, use the ELF format.  */
2257 	      else if ((datasec
2258 			= bfd_get_section_by_name (abfd,
2259 						   MMO_DATA_SECTION_NAME))
2260 		       != NULL
2261 		       && c->value >= datasec->vma
2262 		       && c->value <= datasec->vma + datasec->size)
2263 		{
2264 		  c->section = datasec;
2265 		  c->value -= c->section->vma;
2266 		}
2267 	      else
2268 		c->section = bfd_abs_section_ptr;
2269 	    }
2270 
2271 	  c->udata.p = NULL;
2272 	}
2273     }
2274 
2275   /* Last, overwrite the incoming table with the right-type entries.  */
2276   for (i = 0; i < symcount; i++)
2277     *alocation++ = csymbols++;
2278   *alocation = NULL;
2279 
2280   return symcount;
2281 }
2282 
2283 /* Get information about a symbol.  */
2284 
2285 static void
mmo_get_symbol_info(bfd * ignore_abfd ATTRIBUTE_UNUSED,asymbol * symbol,symbol_info * ret)2286 mmo_get_symbol_info (bfd *ignore_abfd ATTRIBUTE_UNUSED,
2287 		     asymbol *symbol, symbol_info *ret)
2288 {
2289   bfd_symbol_info (symbol, ret);
2290 }
2291 
2292 static void
mmo_print_symbol(bfd * abfd,void * afile,asymbol * symbol,bfd_print_symbol_type how)2293 mmo_print_symbol (bfd *abfd, void *afile, asymbol *symbol,
2294 		  bfd_print_symbol_type how)
2295 {
2296   FILE *file = (FILE *) afile;
2297 
2298   switch (how)
2299     {
2300     case bfd_print_symbol_name:
2301       fprintf (file, "%s", symbol->name);
2302       break;
2303     default:
2304       bfd_print_symbol_vandf (abfd, file, symbol);
2305 
2306       fprintf (file, " %-5s %s",
2307 	       symbol->section->name,
2308 	       symbol->name);
2309     }
2310 }
2311 
2312 /* We can't map a file directly into executable code, so the
2313    size of header information is irrelevant.  */
2314 
2315 static int
mmo_sizeof_headers(bfd * abfd ATTRIBUTE_UNUSED,struct bfd_link_info * info ATTRIBUTE_UNUSED)2316 mmo_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
2317 		    struct bfd_link_info *info ATTRIBUTE_UNUSED)
2318 {
2319   return 0;
2320 }
2321 
2322 /* Write the (section-neutral) file preamble.  */
2323 
2324 static bool
mmo_internal_write_header(bfd * abfd)2325 mmo_internal_write_header (bfd *abfd)
2326 {
2327   const char lop_pre_bfd[] = { LOP, LOP_PRE, 1, 1};
2328 
2329   if (bfd_bwrite (lop_pre_bfd, 4, abfd) != 4)
2330     return false;
2331 
2332   /* Copy creation time of original file.  */
2333   if (bfd_bwrite (abfd->tdata.mmo_data->created, 4, abfd) != 4)
2334     return false;
2335 
2336   return true;
2337 }
2338 
2339 /* Write the LOP_POST record, with global register initializations.
2340    Z is the Z field of the LOP_POST, corresponding to 255 - number of
2341    registers at DATA.  The Z = 255 field is filled in with the
2342    start-address.  */
2343 
2344 static bool
mmo_internal_write_post(bfd * abfd,int z,asection * sec)2345 mmo_internal_write_post (bfd *abfd, int z, asection *sec)
2346 {
2347   int i;
2348   bfd_byte buf[8];
2349   mmo_write_tetra_raw (abfd, (LOP << 24) | (LOP_POST << 16) | z);
2350 
2351   for (i = z; i < 255; i++)
2352     {
2353       bfd_byte *data = mmo_get_loc (sec, i * 8, 8);
2354 
2355       if (bfd_bwrite (data, 8, abfd) != 8)
2356 	return false;
2357     }
2358 
2359   /* For Z == $255, we always emit the start location; supposedly Main,
2360      but we have it handy at bfd_get_start_address.  If we're called with
2361      Z == 255, don't assume DATA is valid.  */
2362   bfd_put_64 (abfd, bfd_get_start_address (abfd), buf);
2363 
2364   return ! abfd->tdata.mmo_data->have_error && bfd_bwrite (buf, 8, abfd) == 8;
2365 }
2366 
2367 /* Translate to and from BFD flags.  This is to make sure that we don't
2368    get bitten by BFD flag number changes.  */
2369 
2370 static flagword
mmo_sec_flags_from_bfd_flags(flagword flags)2371 mmo_sec_flags_from_bfd_flags (flagword flags)
2372 {
2373   flagword oflags = 0;
2374 
2375   if (flags & SEC_ALLOC)
2376     oflags |= MMO_SEC_ALLOC;
2377   if (flags & SEC_LOAD)
2378     oflags |= MMO_SEC_LOAD;
2379   if (flags & SEC_RELOC)
2380     oflags |= MMO_SEC_RELOC;
2381   if (flags & SEC_READONLY)
2382     oflags |= MMO_SEC_READONLY;
2383   if (flags & SEC_CODE)
2384     oflags |= MMO_SEC_CODE;
2385   if (flags & SEC_DATA)
2386     oflags |= MMO_SEC_DATA;
2387   if (flags & SEC_NEVER_LOAD)
2388     oflags |= MMO_SEC_NEVER_LOAD;
2389   if (flags & SEC_IS_COMMON)
2390     oflags |= MMO_SEC_IS_COMMON;
2391   if (flags & SEC_DEBUGGING)
2392     oflags |= MMO_SEC_DEBUGGING;
2393 
2394   return oflags;
2395 }
2396 
2397 static flagword
bfd_sec_flags_from_mmo_flags(flagword flags)2398 bfd_sec_flags_from_mmo_flags (flagword flags)
2399 {
2400   flagword oflags = 0;
2401 
2402   if (flags & MMO_SEC_ALLOC)
2403     oflags |= SEC_ALLOC;
2404   if (flags & MMO_SEC_LOAD)
2405     oflags |= SEC_LOAD;
2406   if (flags & MMO_SEC_RELOC)
2407     oflags |= SEC_RELOC;
2408   if (flags & MMO_SEC_READONLY)
2409     oflags |= SEC_READONLY;
2410   if (flags & MMO_SEC_CODE)
2411     oflags |= SEC_CODE;
2412   if (flags & MMO_SEC_DATA)
2413     oflags |= SEC_DATA;
2414   if (flags & MMO_SEC_NEVER_LOAD)
2415     oflags |= SEC_NEVER_LOAD;
2416   if (flags & MMO_SEC_IS_COMMON)
2417     oflags |= SEC_IS_COMMON;
2418   if (flags & MMO_SEC_DEBUGGING)
2419     oflags |= SEC_DEBUGGING;
2420 
2421   return oflags;
2422 }
2423 
2424 /* Return TRUE iff the leading or trailing tetrabyte in SEC is defined and
2425    is 0.  */
2426 
2427 static bool
mmo_has_leading_or_trailing_zero_tetra_p(bfd * abfd,asection * sec)2428 mmo_has_leading_or_trailing_zero_tetra_p (bfd *abfd, asection *sec)
2429 {
2430   bfd_vma secaddr = bfd_section_vma (sec);
2431 
2432   if (sec->size < 4)
2433     return false;
2434 
2435   if (bfd_get_32 (abfd, mmo_get_loc (sec, secaddr, 4)) == 0
2436       && bfd_get_32 (abfd,
2437 		     mmo_get_loc (sec, secaddr + sec->size - 4, 4)) == 0)
2438     return true;
2439 
2440   return false;
2441 }
2442 
2443 /* Write a section.  */
2444 
2445 static bool
mmo_internal_write_section(bfd * abfd,asection * sec)2446 mmo_internal_write_section (bfd *abfd, asection *sec)
2447 {
2448   /* We do it differently depending on what section this is:
2449 
2450    ".text": Output, prepended by information about the first source file
2451    (not yet implemented.)
2452 
2453    ".data": Output.
2454 
2455    (".MMIX.reg_contents": Not handled here.)
2456 
2457    Anything else: Output inside a lop_spec 80, in the format described
2458    above.  */
2459 
2460   if (strcmp (sec->name, MMO_TEXT_SECTION_NAME) == 0)
2461     {
2462       bfd_vma secaddr = bfd_section_vma (sec);
2463 
2464       /* Because leading and trailing zeros are omitted in output, we need to
2465 	 specify the section boundaries so they're correct when the file
2466 	 is read in again.  That's also the case if this section is
2467 	 specified as not within its usual boundaries or alignments.  */
2468       if (sec->size != 0
2469 	  && (secaddr + sec->size >= (bfd_vma) 1 << 56
2470 	      || (secaddr & 3) != 0
2471 	      || (sec->size & 3) != 0
2472 	      || mmo_has_leading_or_trailing_zero_tetra_p (abfd, sec)))
2473 	{
2474 	  if (!mmo_write_section_description (abfd, sec))
2475 	    return false;
2476 	}
2477 
2478       /* FIXME: Output source file name and line number.  */
2479       return mmo_write_loc_chunk_list (abfd, mmo_section_data (sec)->head);
2480     }
2481   else if (strcmp (sec->name, MMO_DATA_SECTION_NAME) == 0)
2482     {
2483       bfd_vma secaddr = bfd_section_vma (sec);
2484 
2485       /* Same goes as for MMO_TEXT_SECTION_NAME above.  */
2486       if (sec->size != 0
2487 	  && (secaddr < (bfd_vma) 0x20 << 56
2488 	      || secaddr + sec->size >= (bfd_vma) 0x21 << 56
2489 	      || (secaddr & 3) != 0
2490 	      || (sec->size & 3) != 0
2491 	      || mmo_has_leading_or_trailing_zero_tetra_p (abfd, sec)))
2492 	{
2493 	  if (!mmo_write_section_description (abfd, sec))
2494 	    return false;
2495 	}
2496 
2497       return mmo_write_loc_chunk_list (abfd, mmo_section_data (sec)->head);
2498     }
2499   else if (strcmp (sec->name, MMIX_REG_CONTENTS_SECTION_NAME) == 0)
2500     /* Not handled here.  */
2501     {
2502       /* This would normally be an abort call since this can't happen, but
2503 	 we don't do that.  */
2504       bfd_set_error (bfd_error_bad_value);
2505       return false;
2506     }
2507   else if (startswith (sec->name, MMIX_OTHER_SPEC_SECTION_PREFIX))
2508     {
2509       int n = atoi (sec->name + strlen (MMIX_OTHER_SPEC_SECTION_PREFIX));
2510 
2511       mmo_write_tetra_raw (abfd, (LOP << 24) | (LOP_SPEC << 16) | n);
2512       return (! abfd->tdata.mmo_data->have_error
2513 	      && mmo_write_chunk_list (abfd, mmo_section_data (sec)->head));
2514     }
2515   /* Ignore sections that are just allocated or empty; we write out
2516      _contents_ here.  */
2517   else if ((bfd_section_flags (sec) & SEC_HAS_CONTENTS) != 0
2518 	   && sec->size != 0)
2519     {
2520       if (!mmo_write_section_description (abfd, sec))
2521 	return false;
2522 
2523       /* Writing a LOP_LOC ends the LOP_SPEC data, and makes data actually
2524 	 loaded.  */
2525       if (bfd_section_flags (sec) & SEC_LOAD)
2526 	return (! abfd->tdata.mmo_data->have_error
2527 		&& mmo_write_loc_chunk_list (abfd,
2528 					 mmo_section_data (sec)->head));
2529       return (! abfd->tdata.mmo_data->have_error
2530 	      && mmo_write_chunk_list (abfd, mmo_section_data (sec)->head));
2531     }
2532 
2533   /* Some section without contents.  */
2534   return true;
2535 }
2536 
2537 /* Write the description of a section, extended-mmo-style.  */
2538 
2539 static bool
mmo_write_section_description(bfd * abfd,asection * sec)2540 mmo_write_section_description (bfd *abfd, asection *sec)
2541 {
2542   /* Keep the following document-comment formatted the way it is.  */
2543 /*
2544 INODE
2545 mmo section mapping, , Symbol-table, mmo
2546 SUBSECTION
2547 	mmo section mapping
2548 
2549 	The implementation in BFD uses special data type 80 (decimal) to
2550 	encapsulate and describe named sections, containing e.g.@: debug
2551 	information.  If needed, any datum in the encapsulation will be
2552 	quoted using lop_quote.  First comes a 32-bit word holding the
2553 	number of 32-bit words containing the zero-terminated zero-padded
2554 	segment name.  After the name there's a 32-bit word holding flags
2555 	describing the section type.  Then comes a 64-bit big-endian word
2556 	with the section length (in bytes), then another with the section
2557 	start address.  Depending on the type of section, the contents
2558 	might follow, zero-padded to 32-bit boundary.  For a loadable
2559 	section (such as data or code), the contents might follow at some
2560 	later point, not necessarily immediately, as a lop_loc with the
2561 	same start address as in the section description, followed by the
2562 	contents.  This in effect forms a descriptor that must be emitted
2563 	before the actual contents.  Sections described this way must not
2564 	overlap.
2565 
2566 	For areas that don't have such descriptors, synthetic sections are
2567 	formed by BFD.  Consecutive contents in the two memory areas
2568 	@samp{0x0000@dots{}00} to @samp{0x01ff@dots{}ff} and
2569 	@samp{0x2000@dots{}00} to @samp{0x20ff@dots{}ff} are entered in
2570 	sections named <<.text>> and <<.data>> respectively.  If an area
2571 	is not otherwise described, but would together with a neighboring
2572 	lower area be less than @samp{0x40000000} bytes long, it is joined
2573 	with the lower area and the gap is zero-filled.  For other cases,
2574 	a new section is formed, named <<.MMIX.sec.@var{n}>>.  Here,
2575 	@var{n} is a number, a running count through the mmo file,
2576 	starting at 0.
2577 
2578 EXAMPLE
2579 	A loadable section specified as:
2580 
2581 | .section secname,"ax"
2582 | TETRA 1,2,3,4,-1,-2009
2583 | BYTE 80
2584 
2585 	and linked to address @samp{0x4}, is represented by the sequence:
2586 
2587 | 0x98080050 - lop_spec 80
2588 | 0x00000002 - two 32-bit words for the section name
2589 | 0x7365636e - "secn"
2590 | 0x616d6500 - "ame\0"
2591 | 0x00000033 - flags CODE, READONLY, LOAD, ALLOC
2592 | 0x00000000 - high 32 bits of section length
2593 | 0x0000001c - section length is 28 bytes; 6 * 4 + 1 + alignment to 32 bits
2594 | 0x00000000 - high 32 bits of section address
2595 | 0x00000004 - section address is 4
2596 | 0x98010002 - 64 bits with address of following data
2597 | 0x00000000 - high 32 bits of address
2598 | 0x00000004 - low 32 bits: data starts at address 4
2599 | 0x00000001 - 1
2600 | 0x00000002 - 2
2601 | 0x00000003 - 3
2602 | 0x00000004 - 4
2603 | 0xffffffff - -1
2604 | 0xfffff827 - -2009
2605 | 0x50000000 - 80 as a byte, padded with zeros.
2606 
2607 	Note that the lop_spec wrapping does not include the section
2608 	contents.  Compare this to a non-loaded section specified as:
2609 
2610 | .section thirdsec
2611 | TETRA 200001,100002
2612 | BYTE 38,40
2613 
2614 	This, when linked to address @samp{0x200000000000001c}, is
2615 	represented by:
2616 
2617 | 0x98080050 - lop_spec 80
2618 | 0x00000002 - two 32-bit words for the section name
2619 | 0x7365636e - "thir"
2620 | 0x616d6500 - "dsec"
2621 | 0x00000010 - flag READONLY
2622 | 0x00000000 - high 32 bits of section length
2623 | 0x0000000c - section length is 12 bytes; 2 * 4 + 2 + alignment to 32 bits
2624 | 0x20000000 - high 32 bits of address
2625 | 0x0000001c - low 32 bits of address 0x200000000000001c
2626 | 0x00030d41 - 200001
2627 | 0x000186a2 - 100002
2628 | 0x26280000 - 38, 40 as bytes, padded with zeros
2629 
2630 	For the latter example, the section contents must not be
2631 	loaded in memory, and is therefore specified as part of the
2632 	special data.  The address is usually unimportant but might
2633 	provide information for e.g.@: the DWARF 2 debugging format.  */
2634 
2635   mmo_write_tetra_raw (abfd, LOP_SPEC_SECTION);
2636   mmo_write_tetra (abfd, (strlen (sec->name) + 3) / 4);
2637   mmo_write_chunk (abfd, (bfd_byte *) sec->name, strlen (sec->name));
2638   mmo_flush_chunk (abfd);
2639   /* FIXME: We can get debug sections (.debug_line & Co.) with a section
2640      flag still having SEC_RELOC set.  Investigate.  This might be true
2641      for all alien sections; perhaps mmo.em should clear that flag.  Might
2642      be related to weak references.  */
2643   mmo_write_tetra (abfd,
2644 		   mmo_sec_flags_from_bfd_flags (bfd_section_flags (sec)));
2645   mmo_write_octa (abfd, sec->size);
2646   mmo_write_octa (abfd, bfd_section_vma (sec));
2647   return true;
2648 }
2649 
2650 /* We save up all data before output.  */
2651 
2652 static bool
mmo_set_section_contents(bfd * abfd ATTRIBUTE_UNUSED,sec_ptr sec,const void * location,file_ptr offset,bfd_size_type bytes_to_do)2653 mmo_set_section_contents (bfd *abfd ATTRIBUTE_UNUSED, sec_ptr sec,
2654 			  const void *location, file_ptr offset,
2655 			  bfd_size_type bytes_to_do)
2656 {
2657   /* Iterate over diminishing chunk sizes, copying contents.  */
2658   while (bytes_to_do)
2659     {
2660       /* A minor song-and-dance to make sure we're not bitten by the
2661 	 distant possibility of the cast from bfd_vma to int making the
2662 	 chunk zero-sized.  */
2663       int chunk_size
2664 	= (int) bytes_to_do != 0 ? bytes_to_do : MMO_SEC_CONTENTS_CHUNK_SIZE;
2665       bfd_byte *loc;
2666 
2667       do
2668 	loc = mmo_get_loc (sec, sec->vma + offset, chunk_size);
2669       while (loc == NULL && (chunk_size /= 2) != 0);
2670 
2671       if (chunk_size == 0)
2672 	return false;
2673 
2674       memcpy (loc, location, chunk_size);
2675 
2676       location = (bfd_byte *) location + chunk_size;
2677       bytes_to_do -= chunk_size;
2678       offset += chunk_size;
2679     }
2680   return true;
2681 }
2682 
2683 /* Add a symbol to a trie-tree.  */
2684 
2685 static bool
mmo_internal_add_3_sym(bfd * abfd,struct mmo_symbol_trie * rootp,const struct mmo_symbol * symp)2686 mmo_internal_add_3_sym (bfd *abfd, struct mmo_symbol_trie *rootp,
2687 			const struct mmo_symbol *symp)
2688 {
2689   const char *name = symp->name;
2690   struct mmo_symbol_trie *trie = rootp;
2691   struct mmo_symbol_trie **triep = NULL;
2692 
2693   while (*name && trie != NULL)
2694     {
2695       if (*name < trie->symchar)
2696 	{
2697 	  triep = &trie->left;
2698 	  trie = trie->left;
2699 	}
2700       else if (*name > trie->symchar)
2701 	{
2702 	  triep = &trie->right;
2703 	  trie = trie->right;
2704 	}
2705       else if (*name == trie->symchar)
2706 	{
2707 	  triep = &trie->middle;
2708 	  name++;
2709 
2710 	  /* Make sure "trie" points to where we should fill in the
2711 	     current symbol whenever we've iterated through "name".  We
2712 	     would lose the right position if we encounter "foobar" then
2713 	     "foo".  */
2714 	  if (*name)
2715 	    trie = trie->middle;
2716 	}
2717     }
2718 
2719   while (*name != 0)
2720     {
2721       /* Create middle branches for the rest of the characters.  */
2722       trie = bfd_zalloc (abfd, sizeof (struct mmo_symbol_trie));
2723       *triep = trie;
2724       trie->symchar = *name++;
2725       triep = &trie->middle;
2726     }
2727 
2728   /* We discover a duplicate symbol rather late in the process, but still;
2729      we discover it and bail out.  */
2730   if (trie->sym.name != NULL)
2731     {
2732       _bfd_error_handler
2733 	/* xgettext:c-format */
2734 	(_("%pB: invalid symbol table: duplicate symbol `%s'\n"),
2735 	 abfd, trie->sym.name);
2736       bfd_set_error (bfd_error_bad_value);
2737       return false;
2738     }
2739 
2740   memcpy (&trie->sym, symp, sizeof *symp);
2741   return true;
2742 }
2743 
2744 /* Find out the length of the serialized version of a trie in bytes.  */
2745 
2746 static unsigned int
mmo_internal_3_length(bfd * abfd,struct mmo_symbol_trie * trie)2747 mmo_internal_3_length (bfd *abfd, struct mmo_symbol_trie *trie)
2748 {
2749   /* First, one for the control byte.  */
2750   unsigned int length = 1;
2751 
2752   if (trie == NULL)
2753     return 0;
2754 
2755   /* Add in the recursion to the left.  */
2756   length += mmo_internal_3_length (abfd, trie->left);
2757 
2758   /* Add in the middle trie and the character.  */
2759   length += 1 + mmo_internal_3_length (abfd, trie->middle);
2760 
2761   /* Add in the recursion to the right.  */
2762   length += mmo_internal_3_length (abfd, trie->right);
2763 
2764   /* Add in bytes for the symbol (if this is an endnode). */
2765   if (trie->sym.name != NULL)
2766     {
2767       unsigned int serno = trie->sym.serno;
2768 
2769       /* First what it takes to encode the value. */
2770       if (trie->sym.sym_type == mmo_reg_sym)
2771 	length++;
2772       else if (trie->sym.sym_type == mmo_undef_sym)
2773 	length += 2;
2774       else
2775 	{
2776 	  bfd_vma value = trie->sym.value;
2777 
2778 	  /* Coded in one to eight following bytes.  */
2779 	  if (trie->sym.sym_type == mmo_data_sym)
2780 	    value -= (bfd_vma) 0x20 << 56;
2781 
2782 	  do
2783 	    {
2784 	      value >>= 8;
2785 	      length++;
2786 	    }
2787 	  while (value != 0);
2788 	}
2789 
2790       /* Find out what it takes to encode the serial number.  */
2791       do
2792 	{
2793 	  serno >>= 7;
2794 	  length++;
2795 	}
2796       while (serno != 0);
2797     }
2798 
2799   return length;
2800 }
2801 
2802 /* Helper function for outputting the serial number of a symbol, output as
2803    a variant of leb128 (see dwarf2 documentation) which could be called
2804    beb128.  Using a helper function and recursion simplifies debugging.  */
2805 
2806 static void
mmo_beb128_out(bfd * abfd,int serno,int marker)2807 mmo_beb128_out (bfd *abfd, int serno, int marker)
2808 {
2809   if (serno & ~0x7f)
2810     mmo_beb128_out (abfd, serno >> 7, 0);
2811   mmo_write_byte (abfd, marker | (serno & 0x7f));
2812 }
2813 
2814 /* Serialize a trie.  */
2815 
2816 static void
mmo_internal_3_dump(bfd * abfd,struct mmo_symbol_trie * trie)2817 mmo_internal_3_dump (bfd *abfd, struct mmo_symbol_trie *trie)
2818 {
2819   bfd_byte control = 0;
2820 
2821   if (trie == NULL)
2822     return;
2823 
2824   if (trie->left)
2825     control |= MMO3_LEFT;
2826 
2827   if (trie->middle)
2828     control |= MMO3_MIDDLE;
2829 
2830   if (trie->right)
2831     control |= MMO3_RIGHT;
2832 
2833   if (trie->sym.name != NULL)
2834     {
2835       /* Encode the symbol type and length of value bytes.  */
2836       if (trie->sym.sym_type == mmo_reg_sym)
2837 	control |= MMO3_REGQUAL_BITS;
2838       else if (trie->sym.sym_type == mmo_undef_sym)
2839 	control |= MMO3_UNDEF;
2840       else
2841 	{
2842 	  bfd_vma value = trie->sym.value;
2843 
2844 	  /* Coded in 1..8 following bytes.  */
2845 	  if (trie->sym.sym_type == mmo_data_sym)
2846 	    {
2847 	      control |= MMO3_DATA;
2848 	      value -= (bfd_vma) 0x20 << 56;
2849 	    }
2850 
2851 	  do
2852 	    {
2853 	      value >>= 8;
2854 	      control++;
2855 	    }
2856 	  while (value != 0);
2857 	}
2858     }
2859 
2860   /* The control byte is output before recursing.  */
2861   mmo_write_byte (abfd, control);
2862 
2863   mmo_internal_3_dump (abfd, trie->left);
2864 
2865   if (control & MMO3_SYMBITS)
2866     {
2867       mmo_write_byte (abfd, trie->symchar);
2868 
2869       if (trie->sym.name != NULL)
2870 	{
2871 	  if (trie->sym.sym_type == mmo_reg_sym)
2872 	    mmo_write_byte (abfd, trie->sym.value);
2873 	  else if (trie->sym.sym_type == mmo_undef_sym)
2874 	    {
2875 	      mmo_write_byte (abfd, 0);
2876 	      mmo_write_byte (abfd, 0);
2877 	    }
2878 	  else
2879 	    {
2880 	      bfd_vma value = trie->sym.value;
2881 
2882 	      bfd_byte byte_n = control & 15;
2883 
2884 	      /* Coded in 1..8 following bytes.  Note that the value is
2885 		 shifted out big-endian.  */
2886 	      if (trie->sym.sym_type == mmo_data_sym)
2887 		{
2888 		  value -= (bfd_vma) 0x20 << 56;
2889 		  byte_n -= 8;
2890 		}
2891 
2892 	      do
2893 		{
2894 		  mmo_write_byte (abfd, (value >> ((byte_n - 1) * 8)) & 0xff);
2895 		  byte_n--;
2896 		}
2897 	      while (byte_n != 0);
2898 	    }
2899 
2900 	  mmo_beb128_out (abfd, trie->sym.serno, 128);
2901 	}
2902       mmo_internal_3_dump (abfd, trie->middle);
2903     }
2904   mmo_internal_3_dump (abfd, trie->right);
2905 }
2906 
2907 /* Write symbols in mmo format.  Also write the lop_end terminator.  */
2908 
2909 static bool
mmo_write_symbols_and_terminator(bfd * abfd)2910 mmo_write_symbols_and_terminator (bfd *abfd)
2911 {
2912   int count = bfd_get_symcount (abfd);
2913   asymbol **table;
2914   asymbol **orig_table = bfd_get_outsymbols (abfd);
2915   int serno;
2916   struct mmo_symbol_trie root;
2917   int trie_len;
2918   int i;
2919   bfd_byte buf[4];
2920 
2921   /* Create a symbol for "Main".  */
2922   asymbol *fakemain = bfd_make_empty_symbol (abfd);
2923 
2924   fakemain->flags = BSF_GLOBAL;
2925   fakemain->value = bfd_get_start_address (abfd);
2926   fakemain->name = MMIX_START_SYMBOL_NAME;
2927   fakemain->section = bfd_abs_section_ptr;
2928 
2929   memset (&root, 0, sizeof (root));
2930 
2931   /* Make all symbols take a left turn.  */
2932   root.symchar = 0xff;
2933 
2934   /* There must always be a ":Main", so we'll add one if there are no
2935      symbols.  Make sure we have room for it.  */
2936   table = bfd_alloc (abfd, (count + 1) * sizeof (asymbol *));
2937   if (table == NULL)
2938     return false;
2939 
2940   if (count != 0)
2941     memcpy (table, orig_table, count * sizeof (asymbol *));
2942 
2943   /* Move :Main (if there is one) to the first position.  This is
2944      necessary to get the same layout of the trie-tree when linking as
2945      when objcopying the result as in the objcopy.exp test "simple objcopy
2946      of executable".  It also automatically takes care of assigning serial
2947      number 1 to :Main (as is mandatory).  */
2948   for (i = 0; i < count; i++)
2949     if (table[i] != NULL
2950 	&& strcmp (table[i]->name, MMIX_START_SYMBOL_NAME) == 0
2951 	&& (table[i]->flags & (BSF_DEBUGGING|BSF_GLOBAL)) == BSF_GLOBAL)
2952       {
2953 	asymbol *mainsym = table[i];
2954 	bfd_vma mainvalue
2955 	  = (mainsym->value
2956 	     + mainsym->section->output_section->vma
2957 	     + mainsym->section->output_offset);
2958 	memcpy (table + 1, orig_table, i * sizeof (asymbol *));
2959 	table[0] = mainsym;
2960 
2961 	/* Check that the value assigned to :Main is the same as the entry
2962 	   address.  The default linker script asserts this.  This is as
2963 	   good a place as any to check this consistency. */
2964 	if (mainvalue != bfd_get_start_address (abfd)
2965 	    && !mmo_ignore_symbol_consistency (abfd))
2966 	  {
2967 	    /* Arbitrary buffer to hold the printable representation of a
2968 	       vma.  */
2969 	    char vmas_main[40];
2970 	    char vmas_start[40];
2971 	    bfd_vma vma_start = bfd_get_start_address (abfd);
2972 
2973 	    sprintf_vma (vmas_main, mainvalue);
2974 	    sprintf_vma (vmas_start, vma_start);
2975 
2976 	    _bfd_error_handler
2977 	      /* xgettext:c-format */
2978 	      (_("%pB: bad symbol definition: `Main' set to %s rather"
2979 		 " than the start address %s\n"),
2980 	       abfd, vmas_main, vmas_start);
2981 	    bfd_set_error (bfd_error_bad_value);
2982 	    return false;
2983 	  }
2984 	break;
2985       }
2986   if (i == count && count != 0)
2987     {
2988       /* When there are symbols, there must be a :Main.  There was no
2989 	 :Main, so we need to add it manually.  */
2990       memcpy (table + 1, orig_table, count * sizeof (asymbol *));
2991       table[0] = fakemain;
2992       count++;
2993     }
2994 
2995   /* Don't bother inspecting symbols in plugin dummy objects; their
2996      symbols aren't fully inspectable.  */
2997   if ((abfd->flags & BFD_PLUGIN) == 0)
2998     {
2999       for (i = 0, serno = 1; i < count && table[i] != NULL; i++)
3000 	{
3001 	  asymbol *s = table[i];
3002 
3003 	  /* It's not enough to consult bfd_is_local_label, since it does not
3004 	     mean "local" in the sense of linkable-and-observable-after-link.
3005 	     Let's just check the BSF_GLOBAL flag.
3006 
3007 	     Also, don't export symbols with characters not in the
3008 	     allowed set.  */
3009 	  if ((s->flags & (BSF_DEBUGGING|BSF_GLOBAL)) == BSF_GLOBAL
3010 	      && strspn (s->name,
3011 			 valid_mmo_symbol_character_set) == strlen (s->name))
3012 	    {
3013 	      struct mmo_symbol sym;
3014 	      memset (&sym, 0, sizeof (sym));
3015 
3016 	      /* Need to strip const here; strdup:ing would leak and the
3017 		 existing string must be safe to reuse.  */
3018 	      sym.name = (char *) s->name;
3019 	      sym.value =
3020 		s->value
3021 		+ s->section->output_section->vma
3022 		+ s->section->output_offset;
3023 
3024 	      if (bfd_is_und_section (s->section))
3025 		sym.sym_type = mmo_undef_sym;
3026 	      else if (strcmp (s->section->name, MMO_DATA_SECTION_NAME) == 0
3027 		       /* The encoding of data symbols require that the "rest"
3028 			  of the value fits in 6 bytes, so the upper two bytes
3029 			  must be 0x2000.  All other symbols get to be the
3030 			  absolute type.  */
3031 		       && (sym.value >> 48) == 0x2000)
3032 		sym.sym_type = mmo_data_sym;
3033 	      else if (strcmp (s->section->name, MMIX_REG_SECTION_NAME) == 0)
3034 		sym.sym_type = mmo_reg_sym;
3035 	      else if (strcmp (s->section->name,
3036 			       MMIX_REG_CONTENTS_SECTION_NAME) == 0)
3037 		{
3038 		  sym.sym_type = mmo_reg_sym;
3039 		  sym.value /= 8;
3040 		}
3041 	      else
3042 		sym.sym_type = mmo_abs_sym;
3043 
3044 	      /* FIXME: We assume the order of the received symbols is an
3045 		 ordered mapping of the serial numbers.  This is not
3046 		 necessarily true if we e.g. objcopy a mmo file to another and
3047 		 there are gaps in the numbering.  Not sure if this can
3048 		 happen.  Not sure what to do.  */
3049 	      sym.serno = serno++;
3050 
3051 	      if (! mmo_internal_add_3_sym (abfd, &root, &sym))
3052 		return false;
3053 	    }
3054 	}
3055     }
3056 
3057   /* Change the root node to be a ":"-prefix.  */
3058   root.symchar = ':';
3059   root.middle = root.left;
3060   root.right = NULL;
3061   root.left = NULL;
3062 
3063   /* We have to find out if we can fit the whole symbol table in the mmo
3064      symtab.  It would be bad to assume we can always fit it in 262144
3065      bytes.  If we can't, just leave the Main symbol.  */
3066   trie_len = (mmo_internal_3_length (abfd, &root) + 3)/4;
3067 
3068   if (trie_len > 0xffff)
3069     {
3070       /* Test this code by using a lower limit in the test above and check
3071 	 that the single "Main" symbol is emitted and handled properly.
3072 	 There's no specific test-case.  */
3073       struct mmo_symbol sym;
3074 
3075       _bfd_error_handler
3076 	/* xgettext:c-format */
3077 	(_("%pB: warning: symbol table too large for mmo, larger than 65535"
3078 	   " 32-bit words: %d.  Only `Main' will be emitted.\n"),
3079 	 abfd, trie_len);
3080 
3081       memset (&sym, 0, sizeof (sym));
3082       sym.sym_type = mmo_abs_sym;
3083       sym.name = MMIX_START_SYMBOL_NAME;
3084       sym.serno = 1;
3085       sym.value = bfd_get_start_address (abfd);
3086 
3087       /* Then patch up a symbol table to be just the ":Main" symbol.  */
3088       memset (&root, 0, sizeof (root));
3089       root.left = root.middle;
3090       root.symchar = 0xff;
3091       root.middle = NULL;
3092       root.right = NULL;
3093 
3094       if (! mmo_internal_add_3_sym (abfd, &root, &sym))
3095 	return false;
3096 
3097       root.symchar = ':';
3098       root.middle = root.left;
3099       root.right = NULL;
3100       root.left = NULL;
3101 
3102       trie_len = (mmo_internal_3_length (abfd, &root) + 3)/4;
3103     }
3104 
3105   /* Reset the written-bytes counter.  */
3106   abfd->tdata.mmo_data->byte_no = 0;
3107 
3108   /* Put out the lop_stab mark.  */
3109   bfd_put_32 (abfd, (LOP << 24) | (LOP_STAB << 16), buf);
3110   if (bfd_bwrite (buf, 4, abfd) != 4)
3111     return false;
3112 
3113   /* Dump out symbols.  */
3114   mmo_internal_3_dump (abfd, &root);
3115 
3116   if (trie_len != (abfd->tdata.mmo_data->byte_no + 3)/4)
3117     {
3118       /* I haven't seen this trig.  It seems no use claiming this case
3119 	 isn't debugged and abort if we get here.  Instead emit a
3120 	 diagnostic and fail "normally".  */
3121       _bfd_error_handler
3122 	/* xgettext:c-format */
3123 	(_("%pB: internal error, symbol table changed size from %d to %d"
3124 	   " words\n"),
3125 	 abfd, trie_len,
3126 	 (abfd->tdata.mmo_data->byte_no + 3)/4);
3127       bfd_set_error (bfd_error_bad_value);
3128       return false;
3129     }
3130 
3131   /* Dump out remaining bytes in the buffer and handle I/O errors by
3132      propagating errors.  */
3133   if ((abfd->tdata.mmo_data->byte_no % 4) != 0
3134       || abfd->tdata.mmo_data->have_error)
3135     {
3136       memset (abfd->tdata.mmo_data->buf + (abfd->tdata.mmo_data->byte_no % 4),
3137 	      0, 4 - (abfd->tdata.mmo_data->byte_no % 4));
3138 
3139       if (abfd->tdata.mmo_data->have_error
3140 	  || bfd_bwrite (abfd->tdata.mmo_data->buf, 4, abfd) != 4)
3141 	return false;
3142     }
3143 
3144   bfd_put_32 (abfd, (LOP << 24) | (LOP_END << 16) | trie_len, buf);
3145   return bfd_bwrite (buf, 4, abfd) == 4;
3146 }
3147 
3148 /* Write section unless it is the register contents section.  For that, we
3149    instead store the section in the supplied pointer.  This function is
3150    used through bfd_map_over_sections.  */
3151 
3152 static void
mmo_write_section_unless_reg_contents(bfd * abfd,asection * sec,void * p)3153 mmo_write_section_unless_reg_contents (bfd *abfd, asection *sec, void *p)
3154 {
3155   struct mmo_write_sec_info *infop = (struct mmo_write_sec_info *) p;
3156 
3157   if (! infop->retval)
3158     return;
3159 
3160   if (strcmp (sec->name, MMIX_REG_CONTENTS_SECTION_NAME) == 0)
3161     {
3162       infop->reg_section = sec;
3163       return;
3164     }
3165 
3166   /* Exclude the convenience register section.  */
3167   if (strcmp (sec->name, MMIX_REG_SECTION_NAME) == 0)
3168     {
3169       if (bfd_section_flags (sec) & SEC_HAS_CONTENTS)
3170 	{
3171 	  /* Make sure it hasn't got contents.  It seems impossible to
3172 	     make it carry contents, so we don't have a test-case for
3173 	     this.  */
3174 	  _bfd_error_handler
3175 	    /* xgettext:c-format */
3176 	    (_("%pB: internal error, internal register section %pA had"
3177 	       " contents\n"),
3178 	     abfd, sec);
3179 	  bfd_set_error (bfd_error_bad_value);
3180 	  infop->retval = false;
3181 	  return;
3182 	}
3183 
3184       return;
3185     }
3186 
3187   infop->retval = mmo_internal_write_section (abfd, sec);
3188 }
3189 
3190 /* Do the actual output of a file.  Assumes mmo_set_section_contents is
3191    already called. */
3192 
3193 static bool
mmo_write_object_contents(bfd * abfd)3194 mmo_write_object_contents (bfd *abfd)
3195 {
3196   struct mmo_write_sec_info wsecinfo;
3197 
3198   /* First, there are a few words of preamble.  */
3199   if (! mmo_internal_write_header (abfd))
3200     return false;
3201 
3202   wsecinfo.reg_section = NULL;
3203   wsecinfo.retval = true;
3204 
3205   bfd_map_over_sections (abfd, mmo_write_section_unless_reg_contents,
3206 			 &wsecinfo);
3207 
3208   if (! wsecinfo.retval)
3209     return false;
3210 
3211   if (wsecinfo.reg_section != NULL)
3212     {
3213       asection *sec = wsecinfo.reg_section;
3214       unsigned int z = (unsigned int) (sec->vma / 8);
3215 
3216       /* Registers 0..31 must not be global.  Do sanity check on the "vma"
3217 	 of the register contents section and check that it corresponds to
3218 	 the length of the section.  */
3219       if (z < 32 || z >= 255 || (sec->vma & 7) != 0
3220 	  || sec->vma != 256 * 8 - sec->size - 8)
3221 	{
3222 	  bfd_set_error (bfd_error_bad_value);
3223 
3224 	  if (sec->size == 0)
3225 	    /* There must always be at least one such register.  */
3226 	    _bfd_error_handler
3227 	      (_("%pB: no initialized registers; section length 0\n"),
3228 	       abfd);
3229 	  else if (sec->vma > (256 - 32) * 8)
3230 	    /* Provide better error message for the case of too many
3231 	       global registers.  */
3232 	    _bfd_error_handler
3233 	      /* xgettext:c-format */
3234 	      (_("%pB: too many initialized registers; section length %" PRId64),
3235 	       abfd, (int64_t) sec->size);
3236 	  else
3237 	    _bfd_error_handler
3238 	      /* xgettext:c-format */
3239 	      (_("%pB: invalid start address for initialized registers of"
3240 		 " length %" PRId64 ": %#" PRIx64),
3241 	       abfd, (int64_t) sec->size, (uint64_t) sec->vma);
3242 
3243 	  return false;
3244 	}
3245 
3246       if (! mmo_internal_write_post (abfd, z, sec))
3247 	return false;
3248     }
3249   else
3250     if (! mmo_internal_write_post (abfd, 255, NULL))
3251       return false;
3252 
3253   return mmo_write_symbols_and_terminator (abfd);
3254 }
3255 
3256 /* If there's anything in particular in a mmo bfd that we want to free,
3257    make this a real function.  Only do this if you see major memory
3258    thrashing; zealous free:ing will cause unwanted behavior, especially if
3259    you "free" memory allocated with "bfd_alloc", or even "bfd_release" a
3260    block allocated with "bfd_alloc"; they're really allocated from an
3261    obstack, and we don't know what was allocated there since this
3262    particular allocation.  */
3263 
3264 #define	mmo_close_and_cleanup _bfd_generic_close_and_cleanup
3265 #define mmo_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
3266 
3267 /* Perhaps we need to adjust this one; mmo labels (originally) without a
3268    leading ':' might more appropriately be called local.  */
3269 #define mmo_bfd_is_local_label_name bfd_generic_is_local_label_name
3270 #define mmo_bfd_is_target_special_symbol _bfd_bool_bfd_asymbol_false
3271 
3272 #define mmo_get_symbol_version_string \
3273   _bfd_nosymbols_get_symbol_version_string
3274 
3275 /* Is this one really used or defined by anyone?  */
3276 #define mmo_get_lineno _bfd_nosymbols_get_lineno
3277 
3278 /* FIXME: We can do better on this one, if we have a dwarf2 .debug_line
3279    section or if MMO line numbers are implemented.  */
3280 #define mmo_find_nearest_line _bfd_nosymbols_find_nearest_line
3281 #define mmo_find_line _bfd_nosymbols_find_line
3282 #define mmo_find_inliner_info _bfd_nosymbols_find_inliner_info
3283 #define mmo_make_empty_symbol _bfd_generic_make_empty_symbol
3284 #define mmo_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
3285 #define mmo_read_minisymbols _bfd_generic_read_minisymbols
3286 #define mmo_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
3287 
3288 #define mmo_get_section_contents_in_window \
3289   _bfd_generic_get_section_contents_in_window
3290 #define mmo_bfd_get_relocated_section_contents \
3291   bfd_generic_get_relocated_section_contents
3292 #define mmo_bfd_gc_sections bfd_generic_gc_sections
3293 #define mmo_bfd_lookup_section_flags bfd_generic_lookup_section_flags
3294 #define mmo_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
3295 #define mmo_bfd_link_add_symbols _bfd_generic_link_add_symbols
3296 #define mmo_bfd_link_just_syms _bfd_generic_link_just_syms
3297 #define mmo_bfd_copy_link_hash_symbol_type \
3298   _bfd_generic_copy_link_hash_symbol_type
3299 #define mmo_bfd_final_link _bfd_generic_final_link
3300 #define mmo_bfd_link_split_section _bfd_generic_link_split_section
3301 #define mmo_bfd_link_check_relocs  _bfd_generic_link_check_relocs
3302 
3303 /* Strictly speaking, only MMIX uses this restricted format, but let's not
3304    stop anybody from shooting themselves in the foot.  */
3305 #define mmo_set_arch_mach bfd_default_set_arch_mach
3306 #define mmo_bfd_relax_section bfd_generic_relax_section
3307 #define mmo_bfd_merge_sections bfd_generic_merge_sections
3308 #define mmo_bfd_is_group_section bfd_generic_is_group_section
3309 #define mmo_bfd_group_name bfd_generic_group_name
3310 #define mmo_bfd_discard_group bfd_generic_discard_group
3311 #define mmo_section_already_linked \
3312   _bfd_generic_section_already_linked
3313 #define mmo_bfd_define_common_symbol bfd_generic_define_common_symbol
3314 #define mmo_bfd_link_hide_symbol _bfd_generic_link_hide_symbol
3315 #define mmo_bfd_define_start_stop bfd_generic_define_start_stop
3316 
3317 /* We want to copy time of creation, otherwise we'd use
3318    BFD_JUMP_TABLE_COPY (_bfd_generic).  */
3319 #define mmo_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
3320 #define mmo_bfd_copy_private_section_data _bfd_generic_bfd_copy_private_section_data
3321 #define mmo_bfd_copy_private_symbol_data _bfd_generic_bfd_copy_private_symbol_data
3322 #define mmo_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
3323 #define mmo_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
3324 #define mmo_bfd_print_private_bfd_data _bfd_generic_bfd_print_private_bfd_data
3325 
3326 const bfd_target mmix_mmo_vec =
3327 {
3328   "mmo",			/* name */
3329   bfd_target_mmo_flavour,
3330   BFD_ENDIAN_BIG,		/* target byte order */
3331   BFD_ENDIAN_BIG,		/* target headers byte order */
3332 
3333   /* FIXME: Might need adjustments.  */
3334   (HAS_RELOC | EXEC_P |		/* object flags */
3335    HAS_LINENO | HAS_DEBUG |
3336    HAS_SYMS | HAS_LOCALS | WP_TEXT),
3337 
3338   /* FIXME: Might need adjustments.  */
3339   (SEC_CODE | SEC_DATA | SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD
3340    | SEC_READONLY | SEC_EXCLUDE | SEC_DEBUGGING | SEC_IN_MEMORY),
3341 				/* section flags */
3342   0,				/* leading underscore */
3343   ' ',				/* ar_pad_char */
3344   16,				/* ar_max_namelen */
3345   0,				/* match priority.  */
3346   TARGET_KEEP_UNUSED_SECTION_SYMBOLS, /* keep unused section symbols.  */
3347   bfd_getb64, bfd_getb_signed_64, bfd_putb64,
3348   bfd_getb32, bfd_getb_signed_32, bfd_putb32,
3349   bfd_getb16, bfd_getb_signed_16, bfd_putb16,	/* data */
3350   bfd_getb64, bfd_getb_signed_64, bfd_putb64,
3351   bfd_getb32, bfd_getb_signed_32, bfd_putb32,
3352   bfd_getb16, bfd_getb_signed_16, bfd_putb16,	/* hdrs */
3353 
3354   {
3355     _bfd_dummy_target,
3356     mmo_object_p,		/* bfd_check_format */
3357     _bfd_dummy_target,
3358     _bfd_dummy_target,
3359   },
3360   {
3361     _bfd_bool_bfd_false_error,
3362     mmo_mkobject,
3363     _bfd_bool_bfd_false_error,
3364     _bfd_bool_bfd_false_error,
3365   },
3366   {				/* bfd_write_contents */
3367     _bfd_bool_bfd_false_error,
3368     mmo_write_object_contents,
3369     _bfd_bool_bfd_false_error,
3370     _bfd_bool_bfd_false_error,
3371   },
3372 
3373   BFD_JUMP_TABLE_GENERIC (mmo),
3374   BFD_JUMP_TABLE_COPY (mmo),
3375   BFD_JUMP_TABLE_CORE (_bfd_nocore),
3376   BFD_JUMP_TABLE_ARCHIVE (_bfd_noarchive),
3377   BFD_JUMP_TABLE_SYMBOLS (mmo),
3378   BFD_JUMP_TABLE_RELOCS (_bfd_norelocs),
3379   BFD_JUMP_TABLE_WRITE (mmo),
3380   BFD_JUMP_TABLE_LINK (mmo),
3381   BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic),
3382 
3383   NULL,
3384 
3385   NULL
3386 };
3387