View | Details | Raw Unified | Return to bug 48108 | Differences between
and this patch

Collapse All | Expand All | Context: (Patch / File /
)

(-)include/simple-object.h (-12 / +13 lines)
 Lines 45-56   typedef struct simple_object_read_struct simple_ob Link Here 
45
   descriptor, and OFFSET, an offset within the file.  The offset is
45
   descriptor, and OFFSET, an offset within the file.  The offset is
46
   for use with archives, and should be 0 for an ordinary object file.
46
   for use with archives, and should be 0 for an ordinary object file.
47
   The descriptor must remain open until done with the returned
47
   The descriptor must remain open until done with the returned
48
   simple_object_read.  SEGMENT_NAME is used on Mach-O and is required
48
   simple_object_read.  SEGMENT_NAME is used to provide a GNU extension
49
   on that platform: it means to only look at sections within the
49
   to Mach-O.  When provided, only sections within that segment will be
50
   segment with that name.  It is ignored for other object file
50
   considered and, additionally, they will be processed according to a GNU
51
   formats.  On error, this function returns NULL, and sets *ERRMSG to
51
   sub-sectioning extension to Mach-O.  SEGMENT_NAME is ignored for other
52
   an error string and sets *ERR to an errno value or 0 if there is no
52
   object file formats.  On error, this function returns NULL, and sets
53
   relevant errno.  */
53
   *ERRMSG to an error string and sets *ERR to an errno value or 0 if there
54
   is no relevant errno.  */
54
55
55
extern simple_object_read *
56
extern simple_object_read *
56
simple_object_start_read (int descriptor, off_t offset,
57
simple_object_start_read (int descriptor, off_t offset,
 Lines 139-150   typedef struct simple_object_write_struct simple_o Link Here 
139
/* Start creating a new object file which is like ATTRS.  You must
140
/* Start creating a new object file which is like ATTRS.  You must
140
   fetch attribute information from an existing object file before you
141
   fetch attribute information from an existing object file before you
141
   can create a new one.  There is currently no support for creating
142
   can create a new one.  There is currently no support for creating
142
   an object file de novo.  The segment name is only used on Mach-O,
143
   an object file de novo.  SEGMENT_NAME is only used on Mach-O and, if
143
   where it is required.  It means that all sections are created
144
   set, it will cause all sections supplied to be stored according to a
144
   within that segment.  It is ignored for other object file formats.
145
   GNU sub-sectioning extension to the format.  It is ignored for other
145
   On error this function returns NULL, sets *ERRMSG to an error
146
   object file formats.  On error this function returns NULL, sets *ERRMSG
146
   message, and sets *ERR to an errno value or 0 if there isn't
147
   to an error message, and sets *ERR to an errno value or 0 if there
147
   one.  */
148
   isn't one.  */
148
149
149
extern simple_object_write *
150
extern simple_object_write *
150
simple_object_start_write (simple_object_attributes *attrs,
151
simple_object_start_write (simple_object_attributes *attrs,
(-)libiberty/simple-object-mach-o.c (-45 / +160 lines)
 Lines 170-178   struct mach_o_section_64 Link Here 
170
170
171
#define MACH_O_NAME_LEN (16)
171
#define MACH_O_NAME_LEN (16)
172
172
173
/* A GNU specific extension for long section names.  */
173
/* A GNU-specific extension to wrap multiple subsections using three 
174
   mach-o sections within a given segment.  The section '__subsect_sects'
175
   is subdivided according to the index '__subsect_index' and each sub
176
   sect is named according to the names supplied in '__subsect_names'.  */
174
177
175
#define GNU_SECTION_NAMES "__section_names"
178
#define GNU_SECTION_SECTS "__subsect_sects"
179
#define GNU_SECTION_INDEX "__subsect_index"
180
#define GNU_SECTION_NAMES "__subsect_names"
176
181
177
/* Private data for an simple_object_read.  */
182
/* Private data for an simple_object_read.  */
178
183
 Lines 214-221   struct simple_object_mach_o_attributes Link Here 
214
  unsigned int reserved;
219
  unsigned int reserved;
215
};
220
};
216
221
217
/* See if we have a Mach-O file.  */
222
/* See if we have a Mach-O MH_OBJECT file:
218
223
224
   A standard MH_OBJECT (from as) will have three load commands:
225
   0 - LC_SEGMENT/LC_SEGMENT64
226
   1 - LC_SYMTAB
227
   2 - LC_DYSYMTAB
228
   
229
   The LC_SEGMENT/LC_SEGMENT64 will introduce a single anonymous segment
230
   containing all the sections.
231
   
232
   Files written by simple-object will have only the segment command
233
   (no symbol tables).  */
234
219
static void *
235
static void *
220
simple_object_mach_o_match (
236
simple_object_mach_o_match (
221
    unsigned char header[SIMPLE_OBJECT_MATCH_HEADER_LEN],
237
    unsigned char header[SIMPLE_OBJECT_MATCH_HEADER_LEN],
 Lines 258-275   simple_object_mach_o_match ( Link Here 
258
    }
274
    }
259
#endif
275
#endif
260
276
261
  /* We require the user to provide a segment name.  This is
277
  /* Although a standard MH_OBJECT has a single anonymous segment, we allow
262
     unfortunate but I don't see any good choices here.  */
278
     a segment name to be specified - but don't act on it at this stage.  */
263
279
  if (segment_name && strlen (segment_name) > MACH_O_NAME_LEN)
264
  if (segment_name == NULL)
265
    {
280
    {
266
      *errmsg = "Mach-O file found but no segment name specified";
267
      *err = 0;
268
      return NULL;
269
    }
270
271
  if (strlen (segment_name) > MACH_O_NAME_LEN)
272
    {
273
      *errmsg = "Mach-O segment name too long";
281
      *errmsg = "Mach-O segment name too long";
274
      *err = 0;
282
      *err = 0;
275
      return NULL;
283
      return NULL;
 Lines 294-306   simple_object_mach_o_match ( Link Here 
294
  filetype = (*fetch_32) (b + offsetof (struct mach_o_header_32, filetype));
302
  filetype = (*fetch_32) (b + offsetof (struct mach_o_header_32, filetype));
295
  if (filetype != MACH_O_MH_OBJECT)
303
  if (filetype != MACH_O_MH_OBJECT)
296
    {
304
    {
297
      *errmsg = "Mach-O file is not object file";
305
      *errmsg = "Mach-O file is not an MH_OBJECT file";
298
      *err = 0;
306
      *err = 0;
299
      return NULL;
307
      return NULL;
300
    }
308
    }
301
309
302
  omr = XNEW (struct simple_object_mach_o_read);
310
  omr = XNEW (struct simple_object_mach_o_read);
303
  omr->segment_name = xstrdup (segment_name);
311
  if (segment_name)
312
    omr->segment_name = xstrdup (segment_name);
304
  omr->magic = magic;
313
  omr->magic = magic;
305
  omr->is_big_endian = is_big_endian;
314
  omr->is_big_endian = is_big_endian;
306
  omr->cputype = (*fetch_32) (b + offsetof (struct mach_o_header_32, cputype));
315
  omr->cputype = (*fetch_32) (b + offsetof (struct mach_o_header_32, cputype));
 Lines 356-364   simple_object_mach_o_section_info (int is_big_endi Link Here 
356
    }
365
    }
357
}
366
}
358
367
359
/* Handle a segment in a Mach-O file.  Return 1 if we should continue,
368
/* Handle a segment in a Mach-O file.
360
   0 if the caller should return.  */
361
369
370
   This will callback to the function pfn for each section found in the
371
   segment named in 
372
   
373
   We implement a sub-section scheme (which will, in principle, work
374
   with any segment).  At present, likely to be meaningless except for
375
   __GNU_LTO.  
376
   
377
   Return 1 if we should continue, 0 if the caller should return.  */
378
362
static int
379
static int
363
simple_object_mach_o_segment (simple_object_read *sobj, off_t offset,
380
simple_object_mach_o_segment (simple_object_read *sobj, off_t offset,
364
			      const unsigned char *segbuf,
381
			      const unsigned char *segbuf,
 Lines 376-386   simple_object_mach_o_segment (simple_object_read * Link Here 
376
  size_t segname_offset;
393
  size_t segname_offset;
377
  size_t sectname_offset;
394
  size_t sectname_offset;
378
  unsigned int nsects;
395
  unsigned int nsects;
379
  unsigned char *secdata;
396
  unsigned char *secdata = NULL;
380
  unsigned int i;
397
  unsigned int i;
381
  unsigned int strtab_index;
398
  int strtab_index, index_index, sections_index;
382
  char *strtab;
399
  char *strtab = NULL;
383
  size_t strtab_size;
400
  size_t strtab_size = 0;
401
  unsigned char *index = NULL;
402
  size_t index_size;
403
  unsigned int n_lto_sects = 0;
404
  size_t lto_sect_size = 0;
405
  off_t lto_sect_offset = (off_t)0;
384
406
385
  fetch_32 = (omr->is_big_endian
407
  fetch_32 = (omr->is_big_endian
386
	      ? simple_object_fetch_big_32
408
	      ? simple_object_fetch_big_32
 Lines 417-445   simple_object_mach_o_segment (simple_object_read * Link Here 
417
      return 0;
439
      return 0;
418
    }
440
    }
419
441
420
  /* Scan for a __section_names section.  This is in effect a GNU
442
  /* If the user has set a segment name to be processed for GNU sub-sections
421
     extension that permits section names longer than 16 chars.  */
443
     then scan for the three relevant sections.  */
444
  strtab_index = index_index = sections_index = -1;
445
  if (omr->segment_name && strlen (omr->segment_name) > 0)
446
    for (i = 0; i < nsects; ++i)
447
      {
448
	size_t nameoff;
422
449
423
  for (i = 0; i < nsects; ++i)
450
	nameoff = i * sechdrsize + segname_offset;
424
    {
451
	if (strcmp ((char *) secdata + nameoff, omr->segment_name) != 0)
425
      size_t nameoff;
452
	  continue;
426
453
427
      nameoff = i * sechdrsize + segname_offset;
454
	nameoff = i * sechdrsize + sectname_offset;
428
      if (strcmp ((char *) secdata + nameoff, omr->segment_name) != 0)
455
	if (strcmp ((char *) secdata + nameoff, GNU_SECTION_NAMES) == 0)
429
	continue;
456
	  strtab_index = i;
430
      nameoff = i * sechdrsize + sectname_offset;
457
	else if (strcmp ((char *) secdata + nameoff, GNU_SECTION_INDEX) == 0)
431
      if (strcmp ((char *) secdata + nameoff, GNU_SECTION_NAMES) == 0)
458
	  index_index = i;
432
	break;
459
	else if (strcmp ((char *) secdata + nameoff, GNU_SECTION_SECTS) == 0)
433
    }
460
	  sections_index = i;
461
      }
434
462
435
  strtab_index = i;
463
  /* Support code compiled with the orginal LTO implementation of one mach-o 
436
  if (strtab_index >= nsects)
464
     section for each LTO section.  */
465
  if (strtab_index >= 0)
437
    {
466
    {
438
      strtab = NULL;
439
      strtab_size = 0;
440
    }
441
  else
442
    {
443
      off_t strtab_offset;
467
      off_t strtab_offset;
444
468
445
      simple_object_mach_o_section_info (omr->is_big_endian, is_32,
469
      simple_object_mach_o_section_info (omr->is_big_endian, is_32,
 Lines 457-484   simple_object_mach_o_segment (simple_object_read * Link Here 
457
	}
481
	}
458
    }
482
    }
459
483
460
  /* Process the sections.  */
484
  /* The new version puts all the LTO data into a single mach-o section and
485
     provides a separate index from which we implement sub-sectioning.
486
     For now, it is not an error for this to be missing, we could have an
487
     old-style file.  */
488
  if (index_index >= 0)
489
    {
490
      off_t index_offset;
461
491
492
      simple_object_mach_o_section_info (omr->is_big_endian, is_32,
493
					 secdata + index_index * sechdrsize,
494
					 &index_offset, &index_size);
495
      index = XNEWVEC (unsigned char, index_size);
496
      if (!simple_object_internal_read (sobj->descriptor,
497
					sobj->offset + index_offset,
498
					index, index_size,
499
					errmsg, err))
500
	{
501
	  XDELETEVEC (index);
502
	  XDELETEVEC (strtab);
503
	  XDELETEVEC (secdata);
504
	  return 0;
505
	}
506
    }
507
508
  if (sections_index >= 0)
509
    simple_object_mach_o_section_info (omr->is_big_endian, is_32,
510
				       secdata + sections_index * sechdrsize,
511
				       &lto_sect_offset, &lto_sect_size);
512
  /* The index contains 4 uint32_t per sub-section:
513
     sub-section offset/length, sub-section name/length.  
514
     We fix this for both 32 and 64 bit mach-o for now, since other 
515
     fields limit the maximum size of an object to 4G.  */
516
  n_lto_sects = index_size / 16;
517
518
  /* Process the sections:
519
520
     If we have a SEGMENT_NAME and it is finite sized, then fish out the
521
     sub-sections when we encounter the sub-sections entry.  Otherwise 
522
     proceed as below.
523
524
     If we have a strtab and the name matches the form of this, then
525
     substitute the name as per the original scheme.
526
     
527
     Otherwise, the section name is 'segment_name,section_name' in line
528
     with assembler usage.  */
529
462
  for (i = 0; i < nsects; ++i)
530
  for (i = 0; i < nsects; ++i)
463
    {
531
    {
464
      const unsigned char *sechdr;
532
      const unsigned char *sechdr;
465
      char namebuf[MACH_O_NAME_LEN + 1];
533
      char namebuf[MACH_O_NAME_LEN*2 + 2]; /* space for segment,section\0.  */
466
      char *name;
534
      char *name;
467
      off_t secoffset;
535
      off_t secoffset;
468
      size_t secsize;
536
      size_t secsize;
469
537
470
      if (i == strtab_index)
538
      if (i == strtab_index || i == index_index)
471
	continue;
539
	continue;
472
540
473
      sechdr = secdata + i * sechdrsize;
541
      sechdr = secdata + i * sechdrsize;
474
542
475
      if (strcmp ((char *) sechdr + segname_offset, omr->segment_name) != 0)
543
      if (omr->segment_name 
544
	  && strlen (omr->segment_name) > 0
545
	  && strcmp ((char *) sechdr + segname_offset, omr->segment_name) != 0)
476
	continue;
546
	continue;
477
547
548
      if (i == sections_index)
549
	{
550
	/* If we have a new-style file - handle that here.  */
551
	if (n_lto_sects && index)
552
	  {
553
	    int j;
554
	    for (j = 0; j < n_lto_sects; ++j)
555
	      {
556
		unsigned int subsect_offset, subsect_length, name_offset;
557
		subsect_offset = (*fetch_32) (index + 16 * j);
558
		subsect_length = (*fetch_32) (index + 16 * j + 4);
559
		name_offset = (*fetch_32) (index + 16 * j + 8);
560
		/* We don't use the name_length yet.  */
561
	  
562
		secoffset = lto_sect_offset + subsect_offset;
563
		secsize = subsect_length;
564
		name = strtab + name_offset;
565
566
		if (!(*pfn) (data, name, secoffset, secsize))
567
		  {
568
		    *errmsg = NULL;
569
		    *err = 0;
570
		    XDELETEVEC (index);
571
		    XDELETEVEC (strtab);
572
		    XDELETEVEC (secdata);
573
		    return 0;
574
		  }
575
	      }
576
	  }
577
	  continue;
578
	}
579
478
      memcpy (namebuf, sechdr + sectname_offset, MACH_O_NAME_LEN);
580
      memcpy (namebuf, sechdr + sectname_offset, MACH_O_NAME_LEN);
479
      namebuf[MACH_O_NAME_LEN] = '\0';
581
      namebuf[MACH_O_NAME_LEN] = '\0';
480
582
481
      name = &namebuf[0];
583
      name = &namebuf[0];
584
482
      if (strtab != NULL && name[0] == '_' && name[1] == '_')
585
      if (strtab != NULL && name[0] == '_' && name[1] == '_')
483
	{
586
	{
484
	  unsigned long stringoffset;
587
	  unsigned long stringoffset;
 Lines 497-502   simple_object_mach_o_segment (simple_object_read * Link Here 
497
	      name = strtab + stringoffset;
600
	      name = strtab + stringoffset;
498
	    }
601
	    }
499
	}
602
	}
603
      else
604
	{
605
	  /* Compose a section name like __SEGMENT,__section.  */
606
	  size_t l;
607
	  memset (namebuf, 0, MACH_O_NAME_LEN*2+2);
608
	  memcpy (namebuf, (char *) sechdr + segname_offset, MACH_O_NAME_LEN);
609
	  l = strlen (namebuf);
610
	  namebuf[l] = ',';
611
	  memcpy (namebuf, (char *) sechdr + sectname_offset, MACH_O_NAME_LEN);
612
	}
500
613
501
      simple_object_mach_o_section_info (omr->is_big_endian, is_32, sechdr,
614
      simple_object_mach_o_section_info (omr->is_big_endian, is_32, sechdr,
502
					 &secoffset, &secsize);
615
					 &secoffset, &secsize);
 Lines 505-516   simple_object_mach_o_segment (simple_object_read * Link Here 
505
	{
618
	{
506
	  *errmsg = NULL;
619
	  *errmsg = NULL;
507
	  *err = 0;
620
	  *err = 0;
621
	  XDELETEVEC (index);
508
	  XDELETEVEC (strtab);
622
	  XDELETEVEC (strtab);
509
	  XDELETEVEC (secdata);
623
	  XDELETEVEC (secdata);
510
	  return 0;
624
	  return 0;
511
	}
625
	}
512
    }
626
    }
513
627
628
  XDELETEVEC (index);
514
  XDELETEVEC (strtab);
629
  XDELETEVEC (strtab);
515
  XDELETEVEC (secdata);
630
  XDELETEVEC (secdata);
516
631
(-)gcc/config/darwin.c (-52 / +114 lines)
 Lines 1753-1772   darwin_label_is_anonymous_local_objc_name (const c Link Here 
1753
  return (!strncmp ((const char *)p, "_OBJC_", 6));
1753
  return (!strncmp ((const char *)p, "_OBJC_", 6));
1754
}
1754
}
1755
1755
1756
/* LTO support for Mach-O.  */
1756
/* LTO support for Mach-O.
1757
1757
1758
/* Section names for LTO sections.  */
1758
   This version uses three mach-o sections to encapsulate the (unlimited
1759
static unsigned int lto_section_names_offset = 0;
1759
   number of) lto sections.
1760
   
1761
   __GNU_LTO, __lto_sections  contains the concatented GNU LTO section data.
1762
   __GNU_LTO, __section_names contains the GNU LTO section names.
1763
   __GNU_LTO, __section_index contains an array of values that index these.
1760
1764
1761
/* This is the obstack which we use to allocate the many strings.  */
1765
   Indexed thus:
1762
static struct obstack lto_section_names_obstack;
1766
     <section offset from the start of __GNU_LTO, __lto_sections>,
1767
     <section length>
1768
     <name offset from the start of __GNU_LTO, __section_names,
1769
     <name length>.
1763
1770
1764
/* Segment name for LTO sections.  */
1771
   At present, for both m32 and m64 mach-o files each of these fields is
1772
   represented  by a uint32_t.  This is because, AFAICT, a mach-o object
1773
   cannot exceed 4Gb because the section_64 offset field (see below) is 32bits.
1774
   
1775
    uint32_t offset;
1776
   "offset  An integer specifying the offset to this section in the file."  */
1777
1778
/* Count lto section numbers. */
1779
static unsigned int lto_section_num = 0;
1780
1781
/* A vector of information about LTO sections, at present, we only have
1782
   the name.  TODO: see if we can get the data length somehow.  */
1783
typedef struct GTY(()) darwin_lto_section_e {
1784
  const char *sectname;
1785
} darwin_lto_section_e ;
1786
DEF_VEC_O(darwin_lto_section_e);
1787
DEF_VEC_ALLOC_O(darwin_lto_section_e, gc);
1788
1789
static GTY (()) VEC (darwin_lto_section_e, gc) * lto_section_names;
1790
1791
/* Segment for LTO (sub-)sections.  */
1765
#define LTO_SEGMENT_NAME "__GNU_LTO"
1792
#define LTO_SEGMENT_NAME "__GNU_LTO"
1766
1793
1767
/* Section name for LTO section names section.  */
1794
/* Section for LTO sub-sections names.  */
1768
#define LTO_NAMES_SECTION "__section_names"
1795
#define LTO_NAMES_SECTION "__subsect_names"
1769
1796
1797
/* Section for LTO sub-sections index.  */
1798
#define LTO_INDEX_SECTION "__subsect_index"
1799
1800
/* Section for LTO sub-sections.  */
1801
#define LTO_SECTS_SECTION "__subsect_sects"
1802
1770
/* File to temporarily store LTO data.  This is appended to asm_out_file
1803
/* File to temporarily store LTO data.  This is appended to asm_out_file
1771
   in darwin_end_file.  */
1804
   in darwin_end_file.  */
1772
static FILE *lto_asm_out_file, *saved_asm_out_file;
1805
static FILE *lto_asm_out_file, *saved_asm_out_file;
 Lines 1808-1844   darwin_asm_named_section (const char *name, Link Here 
1808
			  unsigned int flags,
1841
			  unsigned int flags,
1809
			  tree decl ATTRIBUTE_UNUSED)
1842
			  tree decl ATTRIBUTE_UNUSED)
1810
{
1843
{
1811
  /* LTO sections go in a special segment __GNU_LTO.  We want to replace the
1844
  /* LTO sections go in a special section that encapsulates the (unlimited)
1812
     section name with something we can use to represent arbitrary-length
1845
     number of GNU LTO sections within a single mach-o one.  */
1813
     names (section names in Mach-O are at most 16 characters long).  */
1814
  if (strncmp (name, LTO_SECTION_NAME_PREFIX,
1846
  if (strncmp (name, LTO_SECTION_NAME_PREFIX,
1815
	       strlen (LTO_SECTION_NAME_PREFIX)) == 0)
1847
	       strlen (LTO_SECTION_NAME_PREFIX)) == 0)
1816
    {
1848
    {
1849
      darwin_lto_section_e e;
1817
      /* We expect certain flags to be set...  */
1850
      /* We expect certain flags to be set...  */
1818
      gcc_assert ((flags & (SECTION_DEBUG | SECTION_NAMED))
1851
      gcc_assert ((flags & (SECTION_DEBUG | SECTION_NAMED))
1819
		  == (SECTION_DEBUG | SECTION_NAMED));
1852
		  == (SECTION_DEBUG | SECTION_NAMED));
1820
1853
1821
      /* Add the section name to the things to output when we end the
1854
      /* Switch to our combined section.  */
1822
	 current assembler output file.
1855
      fprintf (asm_out_file, "\t.section %s,%s,regular,debug\n",
1823
	 This is all not very efficient, but that doesn't matter -- this
1856
	       LTO_SEGMENT_NAME, LTO_SECTS_SECTION);
1824
	 shouldn't be a hot path in the compiler...  */
1857
      /* Output a label for the start of this sub-section.  */
1825
      obstack_1grow (&lto_section_names_obstack, '\t');
1858
      fprintf (asm_out_file, "L_GNU_LTO%d:\t;# %s\n",
1826
      obstack_grow (&lto_section_names_obstack, ".ascii ", 7);
1859
	       lto_section_num, name);
1827
      obstack_1grow (&lto_section_names_obstack, '"');
1860
      /* We have to jump through hoops to get the values of the intra-section
1828
      obstack_grow (&lto_section_names_obstack, name, strlen (name));
1861
         offsets... */
1829
      obstack_grow (&lto_section_names_obstack, "\\0\"\n", 4);
1862
      fprintf (asm_out_file, "\t.set $gnu$lto$offs%d,L_GNU_LTO%d-L_GNU_LTO0\n",
1830
1863
	       lto_section_num, lto_section_num);
1831
      /* Output the dummy section name.  */
1864
      fprintf (asm_out_file, "\t.set $gnu$lto$size%d,L_GNU_LTO%d-L_GNU_LTO%d\n",
1832
      fprintf (asm_out_file, "\t# %s\n", name);
1865
	       lto_section_num, lto_section_num+1, lto_section_num);
1833
      fprintf (asm_out_file, "\t.section %s,__%08X,regular,debug\n",
1866
      lto_section_num++;
1834
	       LTO_SEGMENT_NAME, lto_section_names_offset);
1867
      e.sectname = xstrdup (name);
1835
1868
      /* Keep the names, we'll need to make a table later.
1836
      /* Update the offset for the next section name.  Make sure we stay
1869
         TODO: check that we do not revisit sections, that would break 
1837
	 within reasonable length.  */  
1870
         the assumption of how this is done. */
1838
      lto_section_names_offset += strlen (name) + 1;
1871
      if (lto_section_names == NULL)
1839
      gcc_assert (lto_section_names_offset > 0
1872
        lto_section_names = VEC_alloc (darwin_lto_section_e, gc, 16);
1840
		  && lto_section_names_offset < ((unsigned) 1 << 31));
1873
      VEC_safe_push (darwin_lto_section_e, gc, lto_section_names, &e);
1841
    }
1874
   }
1842
  else if (strncmp (name, "__DWARF,", 8) == 0)
1875
  else if (strncmp (name, "__DWARF,", 8) == 0)
1843
    darwin_asm_dwarf_section (name, flags, decl);
1876
    darwin_asm_dwarf_section (name, flags, decl);
1844
  else
1877
  else
 Lines 2711-2726   darwin_asm_output_dwarf_offset (FILE *file, int si Link Here 
2711
  darwin_asm_output_dwarf_delta (file, size, lab, sname);
2744
  darwin_asm_output_dwarf_delta (file, size, lab, sname);
2712
}
2745
}
2713
2746
2714
/* Called from the within the TARGET_ASM_FILE_START for each target. 
2747
/* Called from the within the TARGET_ASM_FILE_START for each target.  */
2715
  Initialize the stuff we need for LTO long section names support.  */
2716
2748
2717
void
2749
void
2718
darwin_file_start (void)
2750
darwin_file_start (void)
2719
{
2751
{
2720
  /* We fill this obstack with the complete section text for the lto section
2752
  /* Nothing to do.  */
2721
     names to write in darwin_file_end.  */
2722
  obstack_init (&lto_section_names_obstack);
2723
  lto_section_names_offset = 0;
2724
}
2753
}
2725
2754
2726
/* Called for the TARGET_ASM_FILE_END hook.
2755
/* Called for the TARGET_ASM_FILE_END hook.
 Lines 2731-2738   darwin_file_start (void) Link Here 
2731
void
2760
void
2732
darwin_file_end (void)
2761
darwin_file_end (void)
2733
{
2762
{
2734
  const char *lto_section_names;
2735
2736
  machopic_finish (asm_out_file);
2763
  machopic_finish (asm_out_file);
2737
  if (strcmp (lang_hooks.name, "GNU C++") == 0)
2764
  if (strcmp (lang_hooks.name, "GNU C++") == 0)
2738
    {
2765
    {
 Lines 2762-2767   darwin_file_end (void) Link Here 
2762
	  lto_asm_txt = buf = (char *) xmalloc (n + 1);
2789
	  lto_asm_txt = buf = (char *) xmalloc (n + 1);
2763
	  while (fgets (lto_asm_txt, n, lto_asm_out_file))
2790
	  while (fgets (lto_asm_txt, n, lto_asm_out_file))
2764
	    fputs (lto_asm_txt, asm_out_file);
2791
	    fputs (lto_asm_txt, asm_out_file);
2792
	  /* Put a termination label.  */
2793
	  fprintf (asm_out_file, "\t.section %s,%s,regular,debug\n",
2794
		   LTO_SEGMENT_NAME, LTO_SECTS_SECTION);
2795
	  fprintf (asm_out_file, "L_GNU_LTO%d:\t;# end of lto\n",
2796
		   lto_section_num);
2797
	  /* Make sure our termination label stays in this section.  */
2798
	  fputs ("\t.space\t1\n", asm_out_file);
2765
	}
2799
	}
2766
2800
2767
      /* Remove the temporary file.  */
2801
      /* Remove the temporary file.  */
 Lines 2770-2790   darwin_file_end (void) Link Here 
2770
      free (lto_asm_out_name);
2804
      free (lto_asm_out_name);
2771
    }
2805
    }
2772
2806
2773
  /* Finish the LTO section names obstack.  Don't output anything if
2807
  /* Output the names and indices.  */
2774
     there are no recorded section names.  */
2808
  if (lto_section_names && VEC_length (darwin_lto_section_e, lto_section_names))
2775
  obstack_1grow (&lto_section_names_obstack, '\0');
2776
  lto_section_names = XOBFINISH (&lto_section_names_obstack, const char *);
2777
  if (strlen (lto_section_names) > 0)
2778
    {
2809
    {
2779
      fprintf (asm_out_file,
2810
      int count;
2780
	       "\t.section %s,%s,regular,debug\n",
2811
      darwin_lto_section_e *ref;
2812
      /* For now, we'll make the offsets 4 bytes and unaligned - we'll fix
2813
         the latter up ourselves. */
2814
      const char *op = integer_asm_op (4,0); 
2815
2816
      /* Emit the names. */
2817
      fprintf (asm_out_file, "\t.section %s,%s,regular,debug\n",
2781
	       LTO_SEGMENT_NAME, LTO_NAMES_SECTION);
2818
	       LTO_SEGMENT_NAME, LTO_NAMES_SECTION);
2782
      fprintf (asm_out_file,
2819
      FOR_EACH_VEC_ELT (darwin_lto_section_e, lto_section_names, count, ref)
2783
	       "\t# Section names in %s are offsets into this table\n",
2820
	{
2784
	       LTO_SEGMENT_NAME);
2821
	  fprintf (asm_out_file, "L_GNU_LTO_NAME%d:\n", count);
2785
      fprintf (asm_out_file, "%s\n", lto_section_names);
2822
         /* We have to jump through hoops to get the values of the intra-section
2823
            offsets... */
2824
	  fprintf (asm_out_file, 
2825
		   "\t.set $gnu$lto$noff%d,L_GNU_LTO_NAME%d-L_GNU_LTO_NAME0\n",
2826
		   count, count);
2827
	  fprintf (asm_out_file,
2828
		   "\t.set $gnu$lto$nsiz%d,L_GNU_LTO_NAME%d-L_GNU_LTO_NAME%d\n",
2829
		   count, count+1, count);
2830
	  fprintf (asm_out_file, "\t.asciz\t\"%s\"\n", ref->sectname);
2831
	}
2832
      fprintf (asm_out_file, "L_GNU_LTO_NAME%d:\t;# end\n", lto_section_num);
2833
      /* make sure our termination label stays in this section.  */
2834
      fputs ("\t.space\t1\n", asm_out_file);
2835
2836
      /* Emit the Index. */
2837
      fprintf (asm_out_file, "\t.section %s,%s,regular,debug\n",
2838
	       LTO_SEGMENT_NAME, LTO_INDEX_SECTION);
2839
      fputs ("\t.align\t2\n", asm_out_file);
2840
      fputs ("# Section offset, Section length, Name offset, Name length\n", asm_out_file);
2841
      FOR_EACH_VEC_ELT (darwin_lto_section_e, lto_section_names, count, ref)
2842
	{
2843
	  fprintf (asm_out_file, "%s $gnu$lto$offs%d\t;# %s\n",
2844
		   op, count, ref->sectname);
2845
	  fprintf (asm_out_file, "%s $gnu$lto$size%d\n", op, count);
2846
	  fprintf (asm_out_file, "%s $gnu$lto$noff%d\n", op, count);
2847
	  fprintf (asm_out_file, "%s $gnu$lto$nsiz%d\n", op, count);
2848
	}
2786
    }
2849
    }
2787
  obstack_free (&lto_section_names_obstack, NULL);
2788
2850
2789
  /* If we have section anchors, then we must prevent the linker from
2851
  /* If we have section anchors, then we must prevent the linker from
2790
     re-arranging data.  */
2852
     re-arranging data.  */

Return to bug 48108