xref: /illumos-gate/usr/src/cmd/sgs/libld/common/update.c (revision 67ce1dada345581246cd990d73516418f321a793)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 
22 /*
23  *	Copyright (c) 1988 AT&T
24  *	  All Rights Reserved
25  *
26  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
27  * Use is subject to license terms.
28  */
29 
30 /*
31  * Update the new output file image, perform virtual address, offset and
32  * displacement calculations on the program headers and sections headers,
33  * and generate any new output section information.
34  */
35 
36 #define	ELF_TARGET_AMD64
37 
38 #include	<stdio.h>
39 #include	<string.h>
40 #include	<unistd.h>
41 #include	<debug.h>
42 #include	"msg.h"
43 #include	"_libld.h"
44 
45 /*
46  * Comparison routine used by qsort() for sorting of the global symbol list
47  * based off of the hashbuckets the symbol will eventually be deposited in.
48  */
49 static int
50 sym_hash_compare(Sym_s_list * s1, Sym_s_list * s2)
51 {
52 	return (s1->sl_hval - s2->sl_hval);
53 }
54 
55 /*
56  * Comparison routine used by qsort() for sorting of dyn[sym|tls]sort section
57  * indices based on the address of the symbols they reference. The
58  * use of the global dynsort_compare_syms variable is needed because
59  * we need to examine the symbols the indices reference. It is safe, because
60  * the linker is single threaded.
61  */
62 Sym *dynsort_compare_syms;
63 
64 static int
65 dynsort_compare(const void *idx1, const void *idx2)
66 {
67 	Sym *s1 = dynsort_compare_syms + *((const Word *) idx1);
68 	Sym *s2 = dynsort_compare_syms + *((const Word *) idx2);
69 
70 	/*
71 	 * Note: the logical computation for this is
72 	 *	(st_value1 - st_value2)
73 	 * However, that is only correct if the address type is smaller
74 	 * than a pointer. Writing it this way makes it immune to the
75 	 * class (32 or 64-bit) of the linker.
76 	 */
77 	return ((s1->st_value < s2->st_value) ? -1 :
78 	    (s1->st_value > s2->st_value));
79 }
80 
81 
82 /*
83  * Scan the sorted symbols, and issue warnings if there are any duplicate
84  * values in the list. We only do this if -zverbose is set, or we are
85  * running with LD_DEBUG defined
86  *
87  * entry:
88  *	ofl - Output file descriptor
89  *	ldynsym - Pointer to start of .SUNW_ldynsym section that the
90  *		sort section indexes reference.
91  *	symsort - Pointer to start of .SUNW_dynsymsort or .SUNW_dyntlssort
92  *		section.
93  *	n - # of indices in symsort array
94  *	secname - Name of the symsort section.
95  *
96  * exit:
97  *	If the symsort section contains indexes to more than one
98  *	symbol with the same address value, a warning is issued.
99  */
100 static void
101 dynsort_dupwarn(Ofl_desc *ofl, Sym *ldynsym, const char *str,
102     Word *symsort, Word n, const char *secname)
103 {
104 	int zverbose = (ofl->ofl_flags & FLG_OF_VERBOSE) != 0;
105 	Word ndx, cmp_ndx;
106 	Addr addr, cmp_addr;
107 
108 	/* Nothing to do if -zverbose or LD_DEBUG are not active */
109 	if (!(zverbose || DBG_ENABLED))
110 		return;
111 
112 	cmp_ndx = 0;
113 	cmp_addr = ldynsym[symsort[cmp_ndx]].st_value;
114 	for (ndx = 1; ndx < n; ndx++) {
115 		addr = ldynsym[symsort[ndx]].st_value;
116 		if (cmp_addr == addr) {
117 			if (zverbose)
118 				eprintf(ofl->ofl_lml, ERR_WARNING,
119 				    MSG_INTL(MSG_SYM_DUPSORTADDR), secname,
120 				    str + ldynsym[symsort[cmp_ndx]].st_name,
121 				    str + ldynsym[symsort[ndx]].st_name,
122 				    EC_ADDR(addr));
123 			DBG_CALL(Dbg_syms_dup_sort_addr(ofl->ofl_lml, secname,
124 			    str + ldynsym[symsort[cmp_ndx]].st_name,
125 			    str + ldynsym[symsort[ndx]].st_name,
126 			    EC_ADDR(addr)));
127 		} else {	/* Not a dup. Move reference up */
128 			cmp_ndx = ndx;
129 			cmp_addr = addr;
130 		}
131 	}
132 }
133 
134 
135 /*
136  * Build and update any output symbol tables.  Here we work on all the symbol
137  * tables at once to reduce the duplication of symbol and string manipulation.
138  * Symbols and their associated strings are copied from the read-only input
139  * file images to the output image and their values and index's updated in the
140  * output image.
141  */
142 static Addr
143 update_osym(Ofl_desc *ofl)
144 {
145 	/*
146 	 * There are several places in this function where we wish
147 	 * to insert a symbol index to the combined .SUNW_ldynsym/.dynsym
148 	 * symbol table into one of the two sort sections (.SUNW_dynsymsort
149 	 * or .SUNW_dyntlssort), if that symbol has the right attributes.
150 	 * This macro is used to generate the necessary code from a single
151 	 * specification.
152 	 *
153 	 * entry:
154 	 *	_sdp, _sym, _type - As per DYNSORT_COUNT. See _libld.h
155 	 *	_sym_ndx - Index that _sym will have in the combined
156 	 *		.SUNW_ldynsym/.dynsym symbol table.
157 	 */
158 #define	ADD_TO_DYNSORT(_sdp, _sym, _type, _sym_ndx) \
159 	{ \
160 		Word *_dynsort_arr, *_dynsort_ndx; \
161 		\
162 		if (dynsymsort_symtype[_type]) { \
163 			_dynsort_arr = dynsymsort; \
164 			_dynsort_ndx = &dynsymsort_ndx; \
165 		} else if (_type == STT_TLS) { \
166 			_dynsort_arr = dyntlssort; \
167 			_dynsort_ndx = &dyntlssort_ndx; \
168 		} else { \
169 			_dynsort_arr = NULL; \
170 		} \
171 		if ((_dynsort_arr != NULL) && DYNSORT_TEST_ATTR(_sdp, _sym)) \
172 			_dynsort_arr[(*_dynsort_ndx)++] = _sym_ndx; \
173 	}
174 
175 
176 	Listnode	*lnp1;
177 	Sym_desc	*sdp;
178 	Sym_avlnode	*sav;
179 	Sg_desc		*sgp, *tsgp = 0, *dsgp = 0, *esgp = 0;
180 	Os_desc		*osp, *iosp = 0, *fosp = 0;
181 	Ifl_desc	*ifl;
182 	Word		bssndx, etext_ndx, edata_ndx = 0, end_ndx, start_ndx;
183 	Word		end_abs = 0, etext_abs = 0, edata_abs;
184 	Word		tlsbssndx = 0, sunwbssndx = 0, sunwdata1ndx;
185 #if	defined(_ELF64)
186 	Word		lbssndx = 0;
187 	Addr		lbssaddr = 0;
188 #endif
189 	Addr		bssaddr, etext = 0, edata = 0, end = 0, start = 0;
190 	Addr		tlsbssaddr = 0;
191 	Addr 		sunwbssaddr = 0, sunwdata1addr;
192 	int		start_set = 0;
193 	Sym		_sym = {0}, *sym, *symtab = 0;
194 	Sym		*dynsym = 0, *ldynsym = 0;
195 	Word		symtab_ndx = 0;	/* index into .symtab */
196 	Word		ldynsym_ndx = 0;	/* index into .SUNW_ldynsym */
197 	Word		dynsym_ndx = 0;		/* index into .dynsym */
198 	Word		scopesym_ndx = 0; /* index into scoped symbols */
199 	Word		ldynscopesym_ndx = 0; /* index to ldynsym scoped syms */
200 	Word		*dynsymsort = NULL; /* SUNW_dynsymsort index vector */
201 	Word		*dyntlssort = NULL; /* SUNW_dyntlssort index vector */
202 	Word		dynsymsort_ndx;		/* index dynsymsort array */
203 	Word		dyntlssort_ndx;		/* index dyntlssort array */
204 	Word		*symndx;	/* Symbol index (for relocation use) */
205 	Word		*symshndx = 0;	/* .symtab_shndx table */
206 	Word		*dynshndx = 0;	/* .dynsym_shndx table */
207 	Word		*ldynshndx = 0;	/* .SUNW_ldynsym_shndx table */
208 	Word		ldynsym_cnt = 0; /* # of items in .SUNW_ldynsym */
209 	Str_tbl		*shstrtab;
210 	Str_tbl		*strtab;
211 	Str_tbl		*dynstr;
212 	Word		*hashtab;	/* hash table pointer */
213 	Word		*hashbkt;	/* hash table bucket pointer */
214 	Word		*hashchain;	/* hash table chain pointer */
215 	Word		hashval;	/* value of hash function */
216 	Wk_desc		*wkp;
217 	List		weak = {NULL, NULL};
218 	ofl_flag_t	flags = ofl->ofl_flags;
219 	Word		dtflags_1 = ofl->ofl_dtflags_1;
220 	Versym		*versym;
221 	Gottable	*gottable;	/* used for display got debugging */
222 					/*	information */
223 	Syminfo		*syminfo;
224 	Sym_s_list	*sorted_syms;	/* table to hold sorted symbols */
225 	Word		ssndx;		/* global index into sorted_syms */
226 	Word		scndx;		/* scoped index into sorted_syms */
227 	size_t		stoff;		/* string offset */
228 
229 	/*
230 	 * Initialize pointers to the symbol table entries and the symbol
231 	 * table strings.  Skip the first symbol entry and the first string
232 	 * table byte.  Note that if we are not generating any output symbol
233 	 * tables we must still generate and update an internal copies so
234 	 * that the relocation phase has the correct information.
235 	 */
236 	if (!(flags & FLG_OF_STRIP) || (flags & FLG_OF_RELOBJ) ||
237 	    ((flags & FLG_OF_STATIC) && ofl->ofl_osversym)) {
238 		symtab = (Sym *)ofl->ofl_ossymtab->os_outdata->d_buf;
239 		symtab[symtab_ndx++] = _sym;
240 		if (ofl->ofl_ossymshndx)
241 			symshndx =
242 			    (Word *)ofl->ofl_ossymshndx->os_outdata->d_buf;
243 	}
244 	if (OFL_ALLOW_DYNSYM(ofl)) {
245 		dynsym = (Sym *)ofl->ofl_osdynsym->os_outdata->d_buf;
246 		dynsym[dynsym_ndx++] = _sym;
247 		/*
248 		 * If we are also constructing a .SUNW_ldynsym section
249 		 * to contain local function symbols, then set it up too.
250 		 */
251 		if (ofl->ofl_osldynsym) {
252 			ldynsym = (Sym *)ofl->ofl_osldynsym->os_outdata->d_buf;
253 			ldynsym[ldynsym_ndx++] = _sym;
254 			ldynsym_cnt = 1 + ofl->ofl_dynlocscnt +
255 			    ofl->ofl_dynscopecnt;
256 
257 			/*
258 			 * If there is a SUNW_ldynsym, then there may also
259 			 * be a .SUNW_dynsymsort and/or .SUNW_dyntlssort
260 			 * sections, used to collect indices of function
261 			 * and data symbols sorted by address order.
262 			 */
263 			if (ofl->ofl_osdynsymsort) {	/* .SUNW_dynsymsort */
264 				dynsymsort = (Word *)
265 				    ofl->ofl_osdynsymsort->os_outdata->d_buf;
266 				dynsymsort_ndx = 0;
267 			}
268 			if (ofl->ofl_osdyntlssort) {	/* .SUNW_dyntlssort */
269 				dyntlssort = (Word *)
270 				    ofl->ofl_osdyntlssort->os_outdata->d_buf;
271 				dyntlssort_ndx = 0;
272 			}
273 		}
274 
275 		/*
276 		 * Initialize the hash table.
277 		 */
278 		hashtab = (Word *)(ofl->ofl_oshash->os_outdata->d_buf);
279 		hashbkt = &hashtab[2];
280 		hashchain = &hashtab[2 + ofl->ofl_hashbkts];
281 		hashtab[0] = ofl->ofl_hashbkts;
282 		hashtab[1] = ofl->ofl_dynshdrcnt + ofl->ofl_globcnt +
283 		    ofl->ofl_lregsymcnt + 1;
284 		if (ofl->ofl_osdynshndx)
285 			dynshndx =
286 			    (Word *)ofl->ofl_osdynshndx->os_outdata->d_buf;
287 		if (ofl->ofl_osldynshndx)
288 			ldynshndx =
289 			    (Word *)ofl->ofl_osldynshndx->os_outdata->d_buf;
290 	}
291 
292 	/*
293 	 * symndx is the symbol index to be used for relocation processing.  It
294 	 * points to the relevant symtab's (.dynsym or .symtab) symbol ndx.
295 	 */
296 	if (dynsym)
297 		symndx = &dynsym_ndx;
298 	else
299 		symndx = &symtab_ndx;
300 
301 	/*
302 	 * If we have version definitions initialize the version symbol index
303 	 * table.  There is one entry for each symbol which contains the symbols
304 	 * version index.
305 	 */
306 	if (!(flags & FLG_OF_NOVERSEC) &&
307 	    (flags & (FLG_OF_VERNEED | FLG_OF_VERDEF))) {
308 		versym = (Versym *)ofl->ofl_osversym->os_outdata->d_buf;
309 		versym[0] = 0;
310 	} else
311 		versym = 0;
312 
313 	/*
314 	 * If syminfo section exists be prepared to fill it in.
315 	 */
316 	if (ofl->ofl_ossyminfo) {
317 		syminfo = ofl->ofl_ossyminfo->os_outdata->d_buf;
318 		syminfo[0].si_flags = SYMINFO_CURRENT;
319 	} else
320 		syminfo = 0;
321 
322 	/*
323 	 * Setup our string tables.
324 	 */
325 	shstrtab = ofl->ofl_shdrsttab;
326 	strtab = ofl->ofl_strtab;
327 	dynstr = ofl->ofl_dynstrtab;
328 
329 	DBG_CALL(Dbg_syms_sec_title(ofl->ofl_lml));
330 
331 	/*
332 	 * Put output file name to the first .symtab and .SUNW_ldynsym symbol.
333 	 */
334 	if (symtab) {
335 		(void) st_setstring(strtab, ofl->ofl_name, &stoff);
336 		sym = &symtab[symtab_ndx++];
337 		/* LINTED */
338 		sym->st_name = stoff;
339 		sym->st_value = 0;
340 		sym->st_size = 0;
341 		sym->st_info = ELF_ST_INFO(STB_LOCAL, STT_FILE);
342 		sym->st_other = 0;
343 		sym->st_shndx = SHN_ABS;
344 
345 		if (versym && !dynsym)
346 			versym[1] = 0;
347 	}
348 	if (ldynsym) {
349 		(void) st_setstring(dynstr, ofl->ofl_name, &stoff);
350 		sym = &ldynsym[ldynsym_ndx];
351 		/* LINTED */
352 		sym->st_name = stoff;
353 		sym->st_value = 0;
354 		sym->st_size = 0;
355 		sym->st_info = ELF_ST_INFO(STB_LOCAL, STT_FILE);
356 		sym->st_other = 0;
357 		sym->st_shndx = SHN_ABS;
358 
359 		/* Scoped symbols get filled in global loop below */
360 		ldynscopesym_ndx = ldynsym_ndx + 1;
361 		ldynsym_ndx += ofl->ofl_dynscopecnt;
362 	}
363 
364 	/*
365 	 * If we are to display GOT summary information, then allocate
366 	 * the buffer to 'cache' the GOT symbols into now.
367 	 */
368 	if (DBG_ENABLED) {
369 		if ((ofl->ofl_gottable = gottable =
370 		    libld_calloc(ofl->ofl_gotcnt, sizeof (Gottable))) == 0)
371 		return ((Addr)S_ERROR);
372 	}
373 
374 	/*
375 	 * Traverse the program headers.  Determine the last executable segment
376 	 * and the last data segment so that we can update etext and edata. If
377 	 * we have empty segments (reservations) record them for setting _end.
378 	 */
379 	for (LIST_TRAVERSE(&ofl->ofl_segs, lnp1, sgp)) {
380 		Phdr	*phd = &(sgp->sg_phdr);
381 		Os_desc	*osp;
382 		Aliste	idx;
383 
384 		if (phd->p_type == PT_LOAD) {
385 			if (sgp->sg_osdescs != NULL) {
386 				Word	_flags = phd->p_flags & (PF_W | PF_R);
387 
388 				if (_flags == PF_R)
389 					tsgp = sgp;
390 				else if (_flags == (PF_W | PF_R))
391 					dsgp = sgp;
392 			} else if (sgp->sg_flags & FLG_SG_EMPTY)
393 				esgp = sgp;
394 		}
395 
396 		/*
397 		 * Generate a section symbol for each output section.
398 		 */
399 		for (APLIST_TRAVERSE(sgp->sg_osdescs, idx, osp)) {
400 			Word	sectndx;
401 
402 			sym = &_sym;
403 			sym->st_value = osp->os_shdr->sh_addr;
404 			sym->st_info = ELF_ST_INFO(STB_LOCAL, STT_SECTION);
405 			/* LINTED */
406 			sectndx = elf_ndxscn(osp->os_scn);
407 
408 			if (symtab) {
409 				if (sectndx >= SHN_LORESERVE) {
410 					symshndx[symtab_ndx] = sectndx;
411 					sym->st_shndx = SHN_XINDEX;
412 				} else {
413 					/* LINTED */
414 					sym->st_shndx = (Half)sectndx;
415 				}
416 				symtab[symtab_ndx++] = *sym;
417 			}
418 
419 			if (dynsym && (osp->os_flags & FLG_OS_OUTREL))
420 				dynsym[dynsym_ndx++] = *sym;
421 
422 			if ((dynsym == 0) || (osp->os_flags & FLG_OS_OUTREL)) {
423 				if (versym)
424 					versym[*symndx - 1] = 0;
425 				osp->os_scnsymndx = *symndx - 1;
426 				DBG_CALL(Dbg_syms_sec_entry(ofl->ofl_lml,
427 				    osp->os_scnsymndx, sgp, osp));
428 			}
429 
430 			/*
431 			 * Generate the .shstrtab for this section.
432 			 */
433 			(void) st_setstring(shstrtab, osp->os_name, &stoff);
434 			osp->os_shdr->sh_name = (Word)stoff;
435 
436 			/*
437 			 * Find the section index for our special symbols.
438 			 */
439 			if (sgp == tsgp) {
440 				/* LINTED */
441 				etext_ndx = elf_ndxscn(osp->os_scn);
442 			} else if (dsgp == sgp) {
443 				if (osp->os_shdr->sh_type != SHT_NOBITS) {
444 					/* LINTED */
445 					edata_ndx = elf_ndxscn(osp->os_scn);
446 				}
447 			}
448 
449 			if (start_set == 0) {
450 				start = sgp->sg_phdr.p_vaddr;
451 				/* LINTED */
452 				start_ndx = elf_ndxscn(osp->os_scn);
453 				start_set++;
454 			}
455 
456 			/*
457 			 * While we're here, determine whether a .init or .fini
458 			 * section exist.
459 			 */
460 			if ((iosp == 0) && (strcmp(osp->os_name,
461 			    MSG_ORIG(MSG_SCN_INIT)) == 0))
462 				iosp = osp;
463 			if ((fosp == 0) && (strcmp(osp->os_name,
464 			    MSG_ORIG(MSG_SCN_FINI)) == 0))
465 				fosp = osp;
466 		}
467 	}
468 
469 	/*
470 	 * Add local register symbols to the .dynsym.  These are required as
471 	 * DT_REGISTER .dynamic entries must have a symbol to reference.
472 	 */
473 	if (ofl->ofl_regsyms && dynsym) {
474 		int	ndx;
475 
476 		for (ndx = 0; ndx < ofl->ofl_regsymsno; ndx++) {
477 			Sym_desc *	rsdp;
478 
479 			if ((rsdp = ofl->ofl_regsyms[ndx]) == 0)
480 				continue;
481 
482 			if (((rsdp->sd_flags1 & FLG_SY1_HIDDEN) == 0) &&
483 			    (ELF_ST_BIND(rsdp->sd_sym->st_info) != STB_LOCAL))
484 				continue;
485 
486 			dynsym[dynsym_ndx] = *(rsdp->sd_sym);
487 			rsdp->sd_symndx = *symndx;
488 
489 			if (dynsym[dynsym_ndx].st_name) {
490 				(void) st_setstring(dynstr, rsdp->sd_name,
491 				    &stoff);
492 				dynsym[dynsym_ndx].st_name = stoff;
493 			}
494 			dynsym_ndx++;
495 		}
496 	}
497 
498 	/*
499 	 * Having traversed all the output segments, warn the user if the
500 	 * traditional text or data segments don't exist.  Otherwise from these
501 	 * segments establish the values for `etext', `edata', `end', `END',
502 	 * and `START'.
503 	 */
504 	if (!(flags & FLG_OF_RELOBJ)) {
505 		Sg_desc *	sgp;
506 
507 		if (tsgp)
508 			etext = tsgp->sg_phdr.p_vaddr + tsgp->sg_phdr.p_filesz;
509 		else {
510 			etext = (Addr)0;
511 			etext_ndx = SHN_ABS;
512 			etext_abs = 1;
513 			if (flags & FLG_OF_VERBOSE)
514 				eprintf(ofl->ofl_lml, ERR_WARNING,
515 				    MSG_INTL(MSG_UPD_NOREADSEG));
516 		}
517 		if (dsgp) {
518 			edata = dsgp->sg_phdr.p_vaddr + dsgp->sg_phdr.p_filesz;
519 		} else {
520 			edata = (Addr)0;
521 			edata_ndx = SHN_ABS;
522 			edata_abs = 1;
523 			if (flags & FLG_OF_VERBOSE)
524 				eprintf(ofl->ofl_lml, ERR_WARNING,
525 				    MSG_INTL(MSG_UPD_NORDWRSEG));
526 		}
527 
528 		if (dsgp == 0) {
529 			if (tsgp)
530 				sgp = tsgp;
531 			else
532 				sgp = 0;
533 		} else if (tsgp == 0)
534 			sgp = dsgp;
535 		else if (dsgp->sg_phdr.p_vaddr > tsgp->sg_phdr.p_vaddr)
536 			sgp = dsgp;
537 		else if (dsgp->sg_phdr.p_vaddr < tsgp->sg_phdr.p_vaddr)
538 			sgp = tsgp;
539 		else {
540 			/*
541 			 * One of the segments must be of zero size.
542 			 */
543 			if (tsgp->sg_phdr.p_memsz)
544 				sgp = tsgp;
545 			else
546 				sgp = dsgp;
547 		}
548 
549 		if (esgp && (esgp->sg_phdr.p_vaddr > sgp->sg_phdr.p_vaddr))
550 			sgp = esgp;
551 
552 		if (sgp) {
553 			end = sgp->sg_phdr.p_vaddr + sgp->sg_phdr.p_memsz;
554 
555 			/*
556 			 * If the last loadable segment is a read-only segment,
557 			 * then the application which uses the symbol _end to
558 			 * find the beginning of writable heap area may cause
559 			 * segmentation violation. We adjust the value of the
560 			 * _end to skip to the next page boundary.
561 			 *
562 			 * 6401812 System interface which returs beginning
563 			 *	   heap would be nice.
564 			 * When the above RFE is implemented, the changes below
565 			 * could be changed in a better way.
566 			 */
567 			if ((sgp->sg_phdr.p_flags & PF_W) == 0)
568 				end = (Addr)S_ROUND(end, sysconf(_SC_PAGESIZE));
569 
570 			/*
571 			 * If we're dealing with a memory reservation there are
572 			 * no sections to establish an index for _end, so assign
573 			 * it as an absolute.
574 			 */
575 			if (sgp->sg_osdescs != NULL) {
576 				/*
577 				 * Determine the last section for this segment.
578 				 */
579 				Os_desc	*osp = sgp->sg_osdescs->apl_data
580 				    [sgp->sg_osdescs->apl_nitems - 1];
581 
582 				/* LINTED */
583 				end_ndx = elf_ndxscn(osp->os_scn);
584 			} else {
585 				end_ndx = SHN_ABS;
586 				end_abs = 1;
587 			}
588 		} else {
589 			end = (Addr) 0;
590 			end_ndx = SHN_ABS;
591 			end_abs = 1;
592 			eprintf(ofl->ofl_lml, ERR_WARNING,
593 			    MSG_INTL(MSG_UPD_NOSEG));
594 		}
595 	}
596 
597 	DBG_CALL(Dbg_syms_up_title(ofl->ofl_lml));
598 
599 	/*
600 	 * Initialize the scoped symbol table entry point.  This is for all
601 	 * the global symbols that have been scoped to locals and will be
602 	 * filled in during global symbol processing so that we don't have
603 	 * to traverse the globals symbol hash array more than once.
604 	 */
605 	if (symtab) {
606 		scopesym_ndx = symtab_ndx;
607 		symtab_ndx += ofl->ofl_scopecnt;
608 	}
609 
610 	/*
611 	 * Assign .sunwdata1 information
612 	 */
613 	if (ofl->ofl_issunwdata1) {
614 		osp = ofl->ofl_issunwdata1->is_osdesc;
615 		sunwdata1addr = (Addr)(osp->os_shdr->sh_addr +
616 		    ofl->ofl_issunwdata1->is_indata->d_off);
617 		/* LINTED */
618 		sunwdata1ndx = elf_ndxscn(osp->os_scn);
619 		ofl->ofl_sunwdata1ndx = osp->os_scnsymndx;
620 	}
621 
622 	/*
623 	 * If we are generating a .symtab collect all the local symbols,
624 	 * assigning a new virtual address or displacement (value).
625 	 */
626 	for (LIST_TRAVERSE(&ofl->ofl_objs, lnp1, ifl)) {
627 		Xword		lndx, local;
628 		Is_desc *	isc;
629 
630 		/*
631 		 * Check that we have local symbols to process.  If the user
632 		 * has indicated scoping then scan the global symbols also
633 		 * looking for entries from this file to reduce to locals.
634 		 */
635 		if ((local = ifl->ifl_locscnt) == 0)
636 			continue;
637 
638 		for (lndx = 1; lndx < local; lndx++) {
639 			Listnode	*lnp2;
640 			Gotndx		*gnp;
641 			uchar_t		type;
642 			Word		*_symshndx;
643 			int		enter_in_symtab, enter_in_ldynsym;
644 			int		update_done;
645 
646 			sdp = ifl->ifl_oldndx[lndx];
647 			sym = sdp->sd_sym;
648 
649 			/*
650 			 * Assign a got offset if necessary.
651 			 */
652 			if ((ld_targ.t_mr.mr_assign_got != NULL) &&
653 			    (*ld_targ.t_mr.mr_assign_got)(ofl, sdp) == S_ERROR)
654 				return ((Addr)S_ERROR);
655 
656 			if (DBG_ENABLED) {
657 				for (LIST_TRAVERSE(&sdp->sd_GOTndxs,
658 				    lnp2, gnp)) {
659 					gottable->gt_sym = sdp;
660 					gottable->gt_gndx.gn_gotndx =
661 					    gnp->gn_gotndx;
662 					gottable->gt_gndx.gn_addend =
663 					    gnp->gn_addend;
664 					gottable++;
665 				}
666 			}
667 
668 			if ((type = ELF_ST_TYPE(sym->st_info)) == STT_SECTION)
669 				continue;
670 
671 			/*
672 			 * Ignore any symbols that have been marked as invalid
673 			 * during input processing.  Providing these aren't used
674 			 * for relocation they'll just be dropped from the
675 			 * output image.
676 			 */
677 			if (sdp->sd_flags & FLG_SY_INVALID)
678 				continue;
679 
680 			/*
681 			 * If the section that this symbol was associated
682 			 * with has been discarded - then we discard
683 			 * the local symbol along with it.
684 			 */
685 			if (sdp->sd_flags & FLG_SY_ISDISC)
686 				continue;
687 
688 			/*
689 			 * Generate an output symbol to represent this input
690 			 * symbol.  Even if the symbol table is to be stripped
691 			 * we still need to update any local symbols that are
692 			 * used during relocation.
693 			 */
694 			enter_in_symtab = symtab &&
695 			    (!(ofl->ofl_flags & FLG_OF_REDLSYM) ||
696 			    (sdp->sd_psyminfo));
697 			enter_in_ldynsym = ldynsym && sdp->sd_name &&
698 			    ldynsym_symtype[type] &&
699 			    !(ofl->ofl_flags & FLG_OF_REDLSYM);
700 			_symshndx = 0;
701 			if (enter_in_symtab) {
702 				if (!dynsym)
703 					sdp->sd_symndx = *symndx;
704 				symtab[symtab_ndx] = *sym;
705 				/*
706 				 * Provided this isn't an unnamed register
707 				 * symbol, update its name.
708 				 */
709 				if (((sdp->sd_flags & FLG_SY_REGSYM) == 0) ||
710 				    symtab[symtab_ndx].st_name) {
711 					(void) st_setstring(strtab,
712 					    sdp->sd_name, &stoff);
713 					symtab[symtab_ndx].st_name = stoff;
714 				}
715 				sdp->sd_flags &= ~FLG_SY_CLEAN;
716 				if (symshndx)
717 					_symshndx = &symshndx[symtab_ndx];
718 				sdp->sd_sym = sym = &symtab[symtab_ndx++];
719 
720 				if ((sdp->sd_flags & FLG_SY_SPECSEC) &&
721 				    (sym->st_shndx == SHN_ABS) &&
722 				    !enter_in_ldynsym)
723 					continue;
724 			} else if (enter_in_ldynsym) {
725 				/*
726 				 * Not using symtab, but we do have ldynsym
727 				 * available.
728 				 */
729 				ldynsym[ldynsym_ndx] = *sym;
730 				(void) st_setstring(dynstr, sdp->sd_name,
731 				    &stoff);
732 				ldynsym[ldynsym_ndx].st_name = stoff;
733 
734 				sdp->sd_flags &= ~FLG_SY_CLEAN;
735 				if (ldynshndx)
736 					_symshndx = &ldynshndx[ldynsym_ndx];
737 				sdp->sd_sym = sym = &ldynsym[ldynsym_ndx];
738 				/* Add it to sort section if it qualifies */
739 				ADD_TO_DYNSORT(sdp, sym, type, ldynsym_ndx);
740 				ldynsym_ndx++;
741 			} else {	/* Not using symtab or ldynsym */
742 				/*
743 				 * If this symbol requires modifying to provide
744 				 * for a relocation or move table update, make
745 				 * a copy of it.
746 				 */
747 				if (!(sdp->sd_flags & FLG_SY_UPREQD) &&
748 				    !(sdp->sd_psyminfo))
749 					continue;
750 				if ((sdp->sd_flags & FLG_SY_SPECSEC) &&
751 				    (sym->st_shndx == SHN_ABS))
752 					continue;
753 
754 				if (ld_sym_copy(sdp) == S_ERROR)
755 					return ((Addr)S_ERROR);
756 				sym = sdp->sd_sym;
757 			}
758 
759 			/*
760 			 * Update the symbols contents if necessary.
761 			 */
762 			update_done = 0;
763 			if (type == STT_FILE) {
764 				sdp->sd_shndx = sym->st_shndx = SHN_ABS;
765 				sdp->sd_flags |= FLG_SY_SPECSEC;
766 				update_done = 1;
767 			}
768 
769 			/*
770 			 * If we are expanding the locally bound partially
771 			 * initialized symbols, then update the address here.
772 			 */
773 			if (ofl->ofl_issunwdata1 &&
774 			    (sdp->sd_flags & FLG_SY_PAREXPN) && !update_done) {
775 				static	Addr	laddr = 0;
776 
777 				sym->st_shndx = sunwdata1ndx;
778 				sdp->sd_isc = ofl->ofl_issunwdata1;
779 				if (flags & FLG_OF_RELOBJ) {
780 					sym->st_value = sunwdata1addr;
781 				} else {
782 					sym->st_value = laddr;
783 					laddr += sym->st_size;
784 				}
785 				sunwdata1addr += sym->st_size;
786 			}
787 
788 			/*
789 			 * If this isn't an UNDEF symbol (ie. an input section
790 			 * is associated), update the symbols value and index.
791 			 */
792 			if (((isc = sdp->sd_isc) != 0) && !update_done) {
793 				Word	sectndx;
794 
795 				osp = isc->is_osdesc;
796 				/* LINTED */
797 				sym->st_value +=
798 				    (Off)_elf_getxoff(isc->is_indata);
799 				if (!(flags & FLG_OF_RELOBJ)) {
800 					sym->st_value += osp->os_shdr->sh_addr;
801 					/*
802 					 * TLS symbols are relative to
803 					 * the TLS segment.
804 					 */
805 					if ((type == STT_TLS) &&
806 					    (ofl->ofl_tlsphdr)) {
807 						sym->st_value -=
808 						    ofl->ofl_tlsphdr->p_vaddr;
809 					}
810 				}
811 				/* LINTED */
812 				if ((sdp->sd_shndx = sectndx =
813 				    elf_ndxscn(osp->os_scn)) >= SHN_LORESERVE) {
814 					if (_symshndx) {
815 						*_symshndx = sectndx;
816 					}
817 					sym->st_shndx = SHN_XINDEX;
818 				} else {
819 					/* LINTED */
820 					sym->st_shndx = sectndx;
821 				}
822 			}
823 
824 			/*
825 			 * If entering the symbol in both the symtab and the
826 			 * ldynsym, then the one in symtab needs to be
827 			 * copied to ldynsym. If it is only in the ldynsym,
828 			 * then the code above already set it up and we have
829 			 * nothing more to do here.
830 			 */
831 			if (enter_in_symtab && enter_in_ldynsym) {
832 				ldynsym[ldynsym_ndx] = *sym;
833 				(void) st_setstring(dynstr, sdp->sd_name,
834 				    &stoff);
835 				ldynsym[ldynsym_ndx].st_name = stoff;
836 
837 				if (_symshndx && ldynshndx)
838 					ldynshndx[ldynsym_ndx] = *_symshndx;
839 
840 				/* Add it to sort section if it qualifies */
841 				ADD_TO_DYNSORT(sdp, sym, type, ldynsym_ndx);
842 
843 				ldynsym_ndx++;
844 			}
845 		}
846 	}
847 
848 	/*
849 	 * Two special symbols are `_init' and `_fini'.  If these are supplied
850 	 * by crti.o then they are used to represent the total concatenation of
851 	 * the `.init' and `.fini' sections.
852 	 *
853 	 * First, determine whether any .init or .fini sections exist.  If these
854 	 * sections exist when a dynamic object is being built, but no `_init'
855 	 * or `_fini' symbols are found, then the user is probably building this
856 	 * object directly from ld(1) rather than using a compiler driver that
857 	 * provides the symbols via crt's.
858 	 *
859 	 * If the .init or .fini section exist, and their associated symbols,
860 	 * determine the size of the sections and updated the symbols value
861 	 * accordingly.
862 	 */
863 	if (((sdp = ld_sym_find(MSG_ORIG(MSG_SYM_INIT_U), SYM_NOHASH, 0,
864 	    ofl)) != NULL) && (sdp->sd_ref == REF_REL_NEED) && sdp->sd_isc &&
865 	    (sdp->sd_isc->is_osdesc == iosp)) {
866 		if (ld_sym_copy(sdp) == S_ERROR)
867 			return ((Addr)S_ERROR);
868 		sdp->sd_sym->st_size = sdp->sd_isc->is_osdesc->os_shdr->sh_size;
869 
870 	} else if (iosp && !(flags & FLG_OF_RELOBJ)) {
871 		eprintf(ofl->ofl_lml, ERR_WARNING, MSG_INTL(MSG_SYM_NOCRT),
872 		    MSG_ORIG(MSG_SYM_INIT_U), MSG_ORIG(MSG_SCN_INIT));
873 	}
874 
875 	if (((sdp = ld_sym_find(MSG_ORIG(MSG_SYM_FINI_U), SYM_NOHASH, 0,
876 	    ofl)) != NULL) && (sdp->sd_ref == REF_REL_NEED) && sdp->sd_isc &&
877 	    (sdp->sd_isc->is_osdesc == fosp)) {
878 		if (ld_sym_copy(sdp) == S_ERROR)
879 			return ((Addr)S_ERROR);
880 		sdp->sd_sym->st_size = sdp->sd_isc->is_osdesc->os_shdr->sh_size;
881 
882 	} else if (fosp && !(flags & FLG_OF_RELOBJ)) {
883 		eprintf(ofl->ofl_lml, ERR_WARNING, MSG_INTL(MSG_SYM_NOCRT),
884 		    MSG_ORIG(MSG_SYM_FINI_U), MSG_ORIG(MSG_SCN_FINI));
885 	}
886 
887 	/*
888 	 * Assign .bss information for use with updating COMMON symbols.
889 	 */
890 	if (ofl->ofl_isbss) {
891 		osp = ofl->ofl_isbss->is_osdesc;
892 
893 		bssaddr = osp->os_shdr->sh_addr +
894 		    (Off)_elf_getxoff(ofl->ofl_isbss->is_indata);
895 		/* LINTED */
896 		bssndx = elf_ndxscn(osp->os_scn);
897 	}
898 
899 #if	defined(_ELF64)
900 	/*
901 	 * For amd64 target, assign .lbss information for use
902 	 * with updating LCOMMON symbols.
903 	 */
904 	if ((ld_targ.t_m.m_mach == EM_AMD64) && ofl->ofl_islbss) {
905 		osp = ofl->ofl_islbss->is_osdesc;
906 
907 		lbssaddr = osp->os_shdr->sh_addr +
908 		    (Off)_elf_getxoff(ofl->ofl_islbss->is_indata);
909 		/* LINTED */
910 		lbssndx = elf_ndxscn(osp->os_scn);
911 	}
912 #endif
913 
914 	/*
915 	 * Assign .tlsbss information for use with updating COMMON symbols.
916 	 */
917 	if (ofl->ofl_istlsbss) {
918 		osp = ofl->ofl_istlsbss->is_osdesc;
919 		tlsbssaddr = osp->os_shdr->sh_addr +
920 		    (Off)_elf_getxoff(ofl->ofl_istlsbss->is_indata);
921 		/* LINTED */
922 		tlsbssndx = elf_ndxscn(osp->os_scn);
923 	}
924 
925 	/*
926 	 * Assign .SUNW_bss information for use with updating COMMON symbols.
927 	 */
928 	if (ofl->ofl_issunwbss) {
929 		osp = ofl->ofl_issunwbss->is_osdesc;
930 		sunwbssaddr = (Addr)(osp->os_shdr->sh_addr +
931 		    ofl->ofl_issunwbss->is_indata->d_off);
932 		/* LINTED */
933 		sunwbssndx = elf_ndxscn(osp->os_scn);
934 	}
935 
936 
937 	if ((sorted_syms = libld_calloc(ofl->ofl_globcnt +
938 	    ofl->ofl_elimcnt + ofl->ofl_scopecnt, sizeof (*sorted_syms))) == 0)
939 		return ((Addr)S_ERROR);
940 
941 	scndx = 0;
942 	ssndx = ofl->ofl_scopecnt + ofl->ofl_elimcnt;
943 
944 	/*
945 	 * Traverse the internal symbol table updating information and
946 	 * allocating common.
947 	 */
948 	for (sav = avl_first(&ofl->ofl_symavl); sav;
949 	    sav = AVL_NEXT(&ofl->ofl_symavl, sav)) {
950 		Sym *	symptr;
951 		int	local;
952 		int	restore;
953 
954 		sdp = sav->sav_symdesc;
955 
956 		/*
957 		 * Ignore any symbols that have been marked as invalid during
958 		 * input processing.  Providing these aren't used for
959 		 * relocation, they will be dropped from the output image.
960 		 */
961 		if (sdp->sd_flags & FLG_SY_INVALID) {
962 			DBG_CALL(Dbg_syms_old(ofl, sdp));
963 			DBG_CALL(Dbg_syms_ignore(ofl, sdp));
964 			continue;
965 		}
966 
967 		/*
968 		 * Only needed symbols are copied to the output symbol table.
969 		 */
970 		if (sdp->sd_ref == REF_DYN_SEEN)
971 			continue;
972 
973 		if ((sdp->sd_flags1 & FLG_SY1_HIDDEN) &&
974 		    (flags & FLG_OF_PROCRED))
975 			local = 1;
976 		else
977 			local = 0;
978 
979 		if (local || (ofl->ofl_hashbkts == 0)) {
980 			sorted_syms[scndx++].sl_sdp = sdp;
981 		} else {
982 			sorted_syms[ssndx].sl_hval = sdp->sd_aux->sa_hash %
983 			    ofl->ofl_hashbkts;
984 			sorted_syms[ssndx].sl_sdp = sdp;
985 			ssndx++;
986 		}
987 
988 		/*
989 		 * Note - expand the COMMON symbols here because an address
990 		 * must be assigned to them in the same order that space was
991 		 * calculated in sym_validate().  If this ordering isn't
992 		 * followed differing alignment requirements can throw us all
993 		 * out of whack.
994 		 *
995 		 * The expanded .bss global symbol is handled here as well.
996 		 *
997 		 * The actual adding entries into the symbol table still occurs
998 		 * below in hashbucket order.
999 		 */
1000 		symptr = sdp->sd_sym;
1001 		restore = 0;
1002 		if ((sdp->sd_flags & FLG_SY_PAREXPN) ||
1003 		    ((sdp->sd_flags & FLG_SY_SPECSEC) &&
1004 		    (sdp->sd_shndx = symptr->st_shndx) == SHN_COMMON)) {
1005 
1006 			/*
1007 			 * An expanded symbol goes to .sunwdata1.
1008 			 *
1009 			 * A partial initialized global symbol within a shared
1010 			 * object goes to .sunwbss.
1011 			 *
1012 			 * Assign COMMON allocations to .bss.
1013 			 *
1014 			 * Otherwise leave it as is.
1015 			 */
1016 			if (sdp->sd_flags & FLG_SY_PAREXPN) {
1017 				restore = 1;
1018 				sdp->sd_shndx = sunwdata1ndx;
1019 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1020 				symptr->st_value = (Xword) S_ROUND(
1021 				    sunwdata1addr, symptr->st_value);
1022 				sunwdata1addr = symptr->st_value +
1023 				    symptr->st_size;
1024 				sdp->sd_isc = ofl->ofl_issunwdata1;
1025 				sdp->sd_flags |= FLG_SY_COMMEXP;
1026 
1027 			} else if ((sdp->sd_psyminfo != (Psym_info *)NULL) &&
1028 			    (flags & FLG_OF_SHAROBJ) &&
1029 			    (ELF_ST_BIND(symptr->st_info) != STB_LOCAL)) {
1030 				restore = 1;
1031 				sdp->sd_shndx = sunwbssndx;
1032 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1033 				symptr->st_value = (Xword)S_ROUND(sunwbssaddr,
1034 				    symptr->st_value);
1035 				sunwbssaddr = symptr->st_value +
1036 				    symptr->st_size;
1037 				sdp->sd_isc = ofl->ofl_issunwbss;
1038 				sdp->sd_flags |= FLG_SY_COMMEXP;
1039 
1040 			} else if (ELF_ST_TYPE(symptr->st_info) != STT_TLS &&
1041 			    (local || !(flags & FLG_OF_RELOBJ))) {
1042 				restore = 1;
1043 				sdp->sd_shndx = bssndx;
1044 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1045 				symptr->st_value = (Xword)S_ROUND(bssaddr,
1046 				    symptr->st_value);
1047 				bssaddr = symptr->st_value + symptr->st_size;
1048 				sdp->sd_isc = ofl->ofl_isbss;
1049 				sdp->sd_flags |= FLG_SY_COMMEXP;
1050 
1051 			} else if (ELF_ST_TYPE(symptr->st_info) == STT_TLS &&
1052 			    (local || !(flags & FLG_OF_RELOBJ))) {
1053 				restore = 1;
1054 				sdp->sd_shndx = tlsbssndx;
1055 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1056 				symptr->st_value = (Xword)S_ROUND(tlsbssaddr,
1057 				    symptr->st_value);
1058 				tlsbssaddr = symptr->st_value + symptr->st_size;
1059 				sdp->sd_isc = ofl->ofl_istlsbss;
1060 				sdp->sd_flags |= FLG_SY_COMMEXP;
1061 				/*
1062 				 * TLS symbols are relative to the TLS segment.
1063 				 */
1064 				symptr->st_value -= ofl->ofl_tlsphdr->p_vaddr;
1065 			}
1066 #if	defined(_ELF64)
1067 		} else if ((ld_targ.t_m.m_mach == EM_AMD64) &&
1068 		    (sdp->sd_flags & FLG_SY_SPECSEC) &&
1069 		    ((sdp->sd_shndx = symptr->st_shndx) ==
1070 		    SHN_X86_64_LCOMMON) &&
1071 		    ((local || !(flags & FLG_OF_RELOBJ)))) {
1072 			restore = 1;
1073 			sdp->sd_shndx = lbssndx;
1074 			sdp->sd_flags &= ~FLG_SY_SPECSEC;
1075 			symptr->st_value = (Xword)S_ROUND(lbssaddr,
1076 			    symptr->st_value);
1077 			lbssaddr = symptr->st_value + symptr->st_size;
1078 			sdp->sd_isc = ofl->ofl_islbss;
1079 			sdp->sd_flags |= FLG_SY_COMMEXP;
1080 #endif
1081 		}
1082 
1083 		if (restore != 0) {
1084 			uchar_t		type, bind;
1085 
1086 			/*
1087 			 * Make sure this COMMON symbol is returned to the same
1088 			 * binding as was defined in the original relocatable
1089 			 * object reference.
1090 			 */
1091 			type = ELF_ST_TYPE(symptr->st_info);
1092 			if (sdp->sd_flags & FLG_SY_GLOBREF)
1093 				bind = STB_GLOBAL;
1094 			else
1095 				bind = STB_WEAK;
1096 
1097 			symptr->st_info = ELF_ST_INFO(bind, type);
1098 		}
1099 	}
1100 
1101 	if (ofl->ofl_hashbkts) {
1102 		qsort(sorted_syms + ofl->ofl_scopecnt + ofl->ofl_elimcnt,
1103 		    ofl->ofl_globcnt, sizeof (Sym_s_list),
1104 		    (int (*)(const void *, const void *))sym_hash_compare);
1105 	}
1106 
1107 	for (ssndx = 0; ssndx < (ofl->ofl_elimcnt + ofl->ofl_scopecnt +
1108 	    ofl->ofl_globcnt); ssndx++) {
1109 		const char	*name;
1110 		Sym		*sym;
1111 		Sym_aux		*sap;
1112 		Half		spec;
1113 		int		local = 0, dynlocal = 0, enter_in_symtab;
1114 		Listnode	*lnp2;
1115 		Gotndx		*gnp;
1116 		Word		sectndx;
1117 
1118 		sdp = sorted_syms[ssndx].sl_sdp;
1119 		sectndx = 0;
1120 
1121 		if (symtab)
1122 			enter_in_symtab = 1;
1123 		else
1124 			enter_in_symtab = 0;
1125 
1126 		/*
1127 		 * Assign a got offset if necessary.
1128 		 */
1129 		if ((ld_targ.t_mr.mr_assign_got != NULL) &&
1130 		    (*ld_targ.t_mr.mr_assign_got)(ofl, sdp) == S_ERROR)
1131 			return ((Addr)S_ERROR);
1132 
1133 		if (DBG_ENABLED) {
1134 			for (LIST_TRAVERSE(&sdp->sd_GOTndxs, lnp2, gnp)) {
1135 				gottable->gt_sym = sdp;
1136 				gottable->gt_gndx.gn_gotndx = gnp->gn_gotndx;
1137 				gottable->gt_gndx.gn_addend = gnp->gn_addend;
1138 				gottable++;
1139 			}
1140 
1141 			if (sdp->sd_aux && sdp->sd_aux->sa_PLTGOTndx) {
1142 				gottable->gt_sym = sdp;
1143 				gottable->gt_gndx.gn_gotndx =
1144 				    sdp->sd_aux->sa_PLTGOTndx;
1145 				gottable++;
1146 			}
1147 		}
1148 
1149 
1150 		/*
1151 		 * If this symbol has been marked as being reduced to local
1152 		 * scope then it will have to be placed in the scoped portion
1153 		 * of the .symtab.  Retain the appropriate index for use in
1154 		 * version symbol indexing and relocation.
1155 		 */
1156 		if ((sdp->sd_flags1 & FLG_SY1_HIDDEN) &&
1157 		    (flags & FLG_OF_PROCRED)) {
1158 			local = 1;
1159 			if (!(sdp->sd_flags1 & FLG_SY1_ELIM) && !dynsym)
1160 				sdp->sd_symndx = scopesym_ndx;
1161 			else
1162 				sdp->sd_symndx = 0;
1163 
1164 			if (sdp->sd_flags1 & FLG_SY1_ELIM) {
1165 				enter_in_symtab = 0;
1166 			} else if (ldynsym && sdp->sd_sym->st_name &&
1167 			    ldynsym_symtype[
1168 			    ELF_ST_TYPE(sdp->sd_sym->st_info)]) {
1169 				dynlocal = 1;
1170 			}
1171 		} else {
1172 			sdp->sd_symndx = *symndx;
1173 		}
1174 
1175 		/*
1176 		 * Copy basic symbol and string information.
1177 		 */
1178 		name = sdp->sd_name;
1179 		sap = sdp->sd_aux;
1180 
1181 		/*
1182 		 * If we require to record version symbol indexes, update the
1183 		 * associated version symbol information for all defined
1184 		 * symbols.  If a version definition is required any zero value
1185 		 * symbol indexes would have been flagged as undefined symbol
1186 		 * errors, however if we're just scoping these need to fall into
1187 		 * the base of global symbols.
1188 		 */
1189 		if (sdp->sd_symndx && versym) {
1190 			Half	vndx = 0;
1191 
1192 			if (sdp->sd_flags & FLG_SY_MVTOCOMM) {
1193 				vndx = VER_NDX_GLOBAL;
1194 			} else if (sdp->sd_ref == REF_REL_NEED) {
1195 				Half	symflags1 = sdp->sd_flags1;
1196 
1197 				vndx = sap->sa_overndx;
1198 				if ((vndx == 0) &&
1199 				    (sdp->sd_sym->st_shndx != SHN_UNDEF)) {
1200 					if (symflags1 & FLG_SY1_HIDDEN)
1201 						vndx = VER_NDX_LOCAL;
1202 					else
1203 						vndx = VER_NDX_GLOBAL;
1204 				}
1205 			} else if ((sdp->sd_ref == REF_DYN_NEED) &&
1206 			    (sap->sa_dverndx > 0) &&
1207 			    (sap->sa_dverndx <= sdp->sd_file->ifl_vercnt) &&
1208 			    (sdp->sd_file->ifl_verndx != NULL)) {
1209 				/* Use index of verneed record */
1210 				vndx = sdp->sd_file->ifl_verndx
1211 				    [sap->sa_dverndx].vi_overndx;
1212 			}
1213 			versym[sdp->sd_symndx] = vndx;
1214 		}
1215 
1216 		/*
1217 		 * If we are creating the .syminfo section then set per symbol
1218 		 * flags here.
1219 		 */
1220 		if (sdp->sd_symndx && syminfo &&
1221 		    !(sdp->sd_flags & FLG_SY_NOTAVAIL)) {
1222 			int	ndx = sdp->sd_symndx;
1223 			List	*sip = &(ofl->ofl_syminfsyms);
1224 
1225 			if (sdp->sd_flags & FLG_SY_MVTOCOMM)
1226 				/*
1227 				 * Identify a copy relocation symbol.
1228 				 */
1229 				syminfo[ndx].si_flags |= SYMINFO_FLG_COPY;
1230 
1231 			if (sdp->sd_ref == REF_DYN_NEED) {
1232 				/*
1233 				 * A reference is bound to a needed dependency.
1234 				 * Save this symbol descriptor, as its boundto
1235 				 * element will need updating after the .dynamic
1236 				 * section has been created.  Flag whether this
1237 				 * reference is lazy loadable, and if a direct
1238 				 * binding is to be established.
1239 				 */
1240 				if (list_appendc(sip, sdp) == 0)
1241 					return (0);
1242 
1243 				syminfo[ndx].si_flags |= SYMINFO_FLG_DIRECT;
1244 				if (sdp->sd_flags & FLG_SY_LAZYLD)
1245 					syminfo[ndx].si_flags |=
1246 					    SYMINFO_FLG_LAZYLOAD;
1247 
1248 				/*
1249 				 * Enable direct symbol bindings if:
1250 				 *
1251 				 *  .	Symbol was identified with the DIRECT
1252 				 *	keyword in a mapfile.
1253 				 *
1254 				 *  .	Symbol reference has been bound to a
1255 				 * 	dependency which was specified as
1256 				 *	requiring direct bindings with -zdirect.
1257 				 *
1258 				 *  .	All symbol references are required to
1259 				 *	use direct bindings via -Bdirect.
1260 				 */
1261 				if (sdp->sd_flags1 & FLG_SY1_DIR)
1262 					syminfo[ndx].si_flags |=
1263 					    SYMINFO_FLG_DIRECTBIND;
1264 
1265 			} else if ((sdp->sd_flags & FLG_SY_EXTERN) &&
1266 			    (sdp->sd_sym->st_shndx == SHN_UNDEF)) {
1267 				/*
1268 				 * If this symbol has been explicitly defined
1269 				 * as external, and remains unresolved, mark
1270 				 * it as external.
1271 				 */
1272 				syminfo[ndx].si_boundto = SYMINFO_BT_EXTERN;
1273 
1274 			} else if ((sdp->sd_flags & FLG_SY_PARENT) &&
1275 			    (sdp->sd_sym->st_shndx == SHN_UNDEF)) {
1276 				/*
1277 				 * If this symbol has been explicitly defined
1278 				 * to be a reference to a parent object,
1279 				 * indicate whether a direct binding should be
1280 				 * established.
1281 				 */
1282 				syminfo[ndx].si_flags |= SYMINFO_FLG_DIRECT;
1283 				syminfo[ndx].si_boundto = SYMINFO_BT_PARENT;
1284 				if (sdp->sd_flags1 & FLG_SY1_DIR)
1285 					syminfo[ndx].si_flags |=
1286 					    SYMINFO_FLG_DIRECTBIND;
1287 
1288 			} else if (sdp->sd_flags & FLG_SY_STDFLTR) {
1289 				/*
1290 				 * A filter definition.  Although this symbol
1291 				 * can only be a stub, it might be necessary to
1292 				 * prevent external direct bindings.
1293 				 */
1294 				syminfo[ndx].si_flags |= SYMINFO_FLG_FILTER;
1295 				if (sdp->sd_flags1 & FLG_SY1_NDIR)
1296 					syminfo[ndx].si_flags |=
1297 					    SYMINFO_FLG_NOEXTDIRECT;
1298 
1299 			} else if (sdp->sd_flags & FLG_SY_AUXFLTR) {
1300 				/*
1301 				 * An auxiliary filter definition.  By nature,
1302 				 * this definition is direct, in that should the
1303 				 * filtee lookup fail, we'll fall back to this
1304 				 * object.  It may still be necesssary to
1305 				 * prevent external direct bindings.
1306 				 */
1307 				syminfo[ndx].si_flags |= SYMINFO_FLG_AUXILIARY;
1308 				if (sdp->sd_flags1 & FLG_SY1_NDIR)
1309 					syminfo[ndx].si_flags |=
1310 					    SYMINFO_FLG_NOEXTDIRECT;
1311 
1312 			} else if ((sdp->sd_ref == REF_REL_NEED) &&
1313 			    (sdp->sd_sym->st_shndx != SHN_UNDEF)) {
1314 
1315 				/*
1316 				 * This definition exists within the object
1317 				 * being created.  Flag whether it is necessary
1318 				 * to prevent external direct bindings.
1319 				 */
1320 				if (sdp->sd_flags1 & FLG_SY1_NDIR) {
1321 					syminfo[ndx].si_boundto =
1322 					    SYMINFO_BT_NONE;
1323 					syminfo[ndx].si_flags |=
1324 					    SYMINFO_FLG_NOEXTDIRECT;
1325 				}
1326 
1327 				/*
1328 				 * Indicate that this symbol is acting as an
1329 				 * individual interposer.
1330 				 */
1331 				if (sdp->sd_flags & FLG_SY_INTPOSE) {
1332 					syminfo[ndx].si_flags |=
1333 					    SYMINFO_FLG_INTERPOSE;
1334 				}
1335 
1336 				/*
1337 				 * If external bindings are allowed, or this is
1338 				 * a translator symbol, indicate the binding,
1339 				 * and a direct binding if necessary.
1340 				 */
1341 				if (((sdp->sd_flags1 & FLG_SY1_NDIR) == 0) ||
1342 				    ((dtflags_1 & DF_1_TRANS) && sdp->sd_aux &&
1343 				    sdp->sd_aux->sa_bindto)) {
1344 
1345 					syminfo[ndx].si_flags |=
1346 					    SYMINFO_FLG_DIRECT;
1347 
1348 					if (sdp->sd_flags1 & FLG_SY1_DIR)
1349 						syminfo[ndx].si_flags |=
1350 						    SYMINFO_FLG_DIRECTBIND;
1351 
1352 					/*
1353 					 * If this is a translator, the symbols
1354 					 * boundto element will indicate the
1355 					 * dependency to which it should resolve
1356 					 * rather than itself.  Save this info
1357 					 * for updating after the .dynamic
1358 					 * section has been created.
1359 					 */
1360 					if ((dtflags_1 & DF_1_TRANS) &&
1361 					    sdp->sd_aux &&
1362 					    sdp->sd_aux->sa_bindto) {
1363 						if (list_appendc(sip, sdp) == 0)
1364 							return (0);
1365 					} else {
1366 						syminfo[ndx].si_boundto =
1367 						    SYMINFO_BT_SELF;
1368 					}
1369 				}
1370 			}
1371 		}
1372 
1373 		/*
1374 		 * Note that the `sym' value is reset to be one of the new
1375 		 * symbol table entries.  This symbol will be updated further
1376 		 * depending on the type of the symbol.  Process the .symtab
1377 		 * first, followed by the .dynsym, thus the `sym' value will
1378 		 * remain as the .dynsym value when the .dynsym is present.
1379 		 * This ensures that any versioning symbols st_name value will
1380 		 * be appropriate for the string table used by version
1381 		 * entries.
1382 		 */
1383 		if (enter_in_symtab) {
1384 			Word	_symndx;
1385 
1386 			if (local)
1387 				_symndx = scopesym_ndx;
1388 			else
1389 				_symndx = symtab_ndx;
1390 
1391 			symtab[_symndx] = *sdp->sd_sym;
1392 			sdp->sd_sym = sym = &symtab[_symndx];
1393 			(void) st_setstring(strtab, name, &stoff);
1394 			sym->st_name = stoff;
1395 		}
1396 		if (dynlocal) {
1397 			ldynsym[ldynscopesym_ndx] = *sdp->sd_sym;
1398 			sdp->sd_sym = sym = &ldynsym[ldynscopesym_ndx];
1399 			(void) st_setstring(dynstr, name, &stoff);
1400 			ldynsym[ldynscopesym_ndx].st_name = stoff;
1401 			/* Add it to sort section if it qualifies */
1402 			ADD_TO_DYNSORT(sdp, sym, ELF_ST_TYPE(sym->st_info),
1403 			    ldynscopesym_ndx);
1404 		}
1405 
1406 		if (dynsym && !local) {
1407 			dynsym[dynsym_ndx] = *sdp->sd_sym;
1408 
1409 			/*
1410 			 * Provided this isn't an unnamed register symbol,
1411 			 * update the symbols name and hash value.
1412 			 */
1413 			if (((sdp->sd_flags & FLG_SY_REGSYM) == 0) ||
1414 			    dynsym[dynsym_ndx].st_name) {
1415 				(void) st_setstring(dynstr, name, &stoff);
1416 				dynsym[dynsym_ndx].st_name = stoff;
1417 
1418 				if (stoff) {
1419 					Word _hashndx;
1420 
1421 					hashval =
1422 					    sap->sa_hash % ofl->ofl_hashbkts;
1423 
1424 					/* LINTED */
1425 					if (_hashndx = hashbkt[hashval]) {
1426 						while (hashchain[_hashndx]) {
1427 							_hashndx =
1428 							    hashchain[_hashndx];
1429 						}
1430 						hashchain[_hashndx] =
1431 						    sdp->sd_symndx;
1432 					} else {
1433 						hashbkt[hashval] =
1434 						    sdp->sd_symndx;
1435 					}
1436 				}
1437 			}
1438 			sdp->sd_sym = sym = &dynsym[dynsym_ndx];
1439 
1440 			/*
1441 			 * Add it to sort section if it qualifies.
1442 			 * The indexes in that section are relative to the
1443 			 * the adjacent SUNW_ldynsym/dymsym pair, so we
1444 			 * add the number of items in SUNW_ldynsym to the
1445 			 * dynsym index.
1446 			 */
1447 			ADD_TO_DYNSORT(sdp, sym, ELF_ST_TYPE(sym->st_info),
1448 			    ldynsym_cnt + dynsym_ndx);
1449 		}
1450 		if (!enter_in_symtab && (!dynsym || (local && !dynlocal))) {
1451 			if (!(sdp->sd_flags & FLG_SY_UPREQD))
1452 				continue;
1453 			sym = sdp->sd_sym;
1454 		} else
1455 			sdp->sd_flags &= ~FLG_SY_CLEAN;
1456 
1457 
1458 		/*
1459 		 * If we have a weak data symbol for which we need the real
1460 		 * symbol also, save this processing until later.
1461 		 *
1462 		 * The exception to this is if the weak/strong have PLT's
1463 		 * assigned to them.  In that case we don't do the post-weak
1464 		 * processing because the PLT's must be maintained so that we
1465 		 * can do 'interpositioning' on both of the symbols.
1466 		 */
1467 		if ((sap->sa_linkndx) &&
1468 		    (ELF_ST_BIND(sym->st_info) == STB_WEAK) &&
1469 		    (!sap->sa_PLTndx)) {
1470 			Sym_desc *	_sdp =
1471 			    sdp->sd_file->ifl_oldndx[sap->sa_linkndx];
1472 
1473 			if (_sdp->sd_ref != REF_DYN_SEEN) {
1474 				if ((wkp =
1475 				    libld_calloc(sizeof (Wk_desc), 1)) == 0)
1476 					return ((Addr)S_ERROR);
1477 
1478 				if (enter_in_symtab) {
1479 					if (local)
1480 						wkp->wk_symtab =
1481 						    &symtab[scopesym_ndx];
1482 					else
1483 						wkp->wk_symtab =
1484 						    &symtab[symtab_ndx];
1485 				}
1486 				if (dynsym) {
1487 					if (!local) {
1488 						wkp->wk_dynsym =
1489 						    &dynsym[dynsym_ndx];
1490 					} else if (dynlocal) {
1491 						wkp->wk_dynsym =
1492 						    &ldynsym[ldynscopesym_ndx];
1493 					}
1494 				}
1495 				wkp->wk_weak = sdp;
1496 				wkp->wk_alias = _sdp;
1497 
1498 				if (!(list_appendc(&weak, wkp)))
1499 					return ((Addr)S_ERROR);
1500 
1501 				if (enter_in_symtab)
1502 					if (local)
1503 						scopesym_ndx++;
1504 					else
1505 						symtab_ndx++;
1506 				if (dynsym) {
1507 					if (!local) {
1508 						dynsym_ndx++;
1509 					} else if (dynlocal) {
1510 						ldynscopesym_ndx++;
1511 					}
1512 				}
1513 				continue;
1514 			}
1515 		}
1516 
1517 		DBG_CALL(Dbg_syms_old(ofl, sdp));
1518 
1519 		spec = NULL;
1520 		/*
1521 		 * assign new symbol value.
1522 		 */
1523 		sectndx = sdp->sd_shndx;
1524 		if (sectndx == SHN_UNDEF) {
1525 			if (((sdp->sd_flags & FLG_SY_REGSYM) == 0) &&
1526 			    (sym->st_value != 0)) {
1527 				eprintf(ofl->ofl_lml, ERR_WARNING,
1528 				    MSG_INTL(MSG_SYM_NOTNULL),
1529 				    demangle(name), sdp->sd_file->ifl_name);
1530 			}
1531 
1532 			/*
1533 			 * Undefined weak global, if we are generating a static
1534 			 * executable, output as an absolute zero.  Otherwise
1535 			 * leave it as is, ld.so.1 will skip symbols of this
1536 			 * type (this technique allows applications and
1537 			 * libraries to test for the existence of a symbol as an
1538 			 * indication of the presence or absence of certain
1539 			 * functionality).
1540 			 */
1541 			if (((flags & (FLG_OF_STATIC | FLG_OF_EXEC)) ==
1542 			    (FLG_OF_STATIC | FLG_OF_EXEC)) &&
1543 			    (ELF_ST_BIND(sym->st_info) == STB_WEAK)) {
1544 				sdp->sd_flags |= FLG_SY_SPECSEC;
1545 				sdp->sd_shndx = sectndx = SHN_ABS;
1546 			}
1547 		} else if ((sdp->sd_flags & FLG_SY_SPECSEC) &&
1548 		    (sectndx == SHN_COMMON)) {
1549 			/* COMMONs have already been processed */
1550 			/* EMPTY */
1551 			;
1552 		} else {
1553 			if ((sdp->sd_flags & FLG_SY_SPECSEC) &&
1554 			    (sectndx == SHN_ABS))
1555 				spec = sdp->sd_aux->sa_symspec;
1556 
1557 			/* LINTED */
1558 			if (sdp->sd_flags & FLG_SY_COMMEXP) {
1559 				/*
1560 				 * This is (or was) a COMMON symbol which was
1561 				 * processed above - no processing
1562 				 * required here.
1563 				 */
1564 				;
1565 			} else if (sdp->sd_ref == REF_DYN_NEED) {
1566 				uchar_t	type, bind;
1567 
1568 				sectndx = SHN_UNDEF;
1569 				sym->st_value = 0;
1570 				sym->st_size = 0;
1571 
1572 				/*
1573 				 * Make sure this undefined symbol is returned
1574 				 * to the same binding as was defined in the
1575 				 * original relocatable object reference.
1576 				 */
1577 				type = ELF_ST_TYPE(sym-> st_info);
1578 				if (sdp->sd_flags & FLG_SY_GLOBREF)
1579 					bind = STB_GLOBAL;
1580 				else
1581 					bind = STB_WEAK;
1582 
1583 				sym->st_info = ELF_ST_INFO(bind, type);
1584 
1585 			} else if (((sdp->sd_flags & FLG_SY_SPECSEC) == 0) &&
1586 			    (sdp->sd_ref == REF_REL_NEED)) {
1587 				osp = sdp->sd_isc->is_osdesc;
1588 				/* LINTED */
1589 				sectndx = elf_ndxscn(osp->os_scn);
1590 
1591 				/*
1592 				 * In an executable, the new symbol value is the
1593 				 * old value (offset into defining section) plus
1594 				 * virtual address of defining section.  In a
1595 				 * relocatable, the new value is the old value
1596 				 * plus the displacement of the section within
1597 				 * the file.
1598 				 */
1599 				/* LINTED */
1600 				sym->st_value +=
1601 				    (Off)_elf_getxoff(sdp->sd_isc->is_indata);
1602 
1603 				if (!(flags & FLG_OF_RELOBJ)) {
1604 					sym->st_value += osp->os_shdr->sh_addr;
1605 					/*
1606 					 * TLS symbols are relative to
1607 					 * the TLS segment.
1608 					 */
1609 					if ((ELF_ST_TYPE(sym->st_info) ==
1610 					    STT_TLS) && (ofl->ofl_tlsphdr))
1611 						sym->st_value -=
1612 						    ofl->ofl_tlsphdr->p_vaddr;
1613 				}
1614 			}
1615 		}
1616 
1617 		if (spec) {
1618 			switch (spec) {
1619 			case SDAUX_ID_ETEXT:
1620 				sym->st_value = etext;
1621 				sectndx = etext_ndx;
1622 				if (etext_abs)
1623 					sdp->sd_flags |= FLG_SY_SPECSEC;
1624 				else
1625 					sdp->sd_flags &= ~FLG_SY_SPECSEC;
1626 				break;
1627 			case SDAUX_ID_EDATA:
1628 				sym->st_value = edata;
1629 				sectndx = edata_ndx;
1630 				if (edata_abs)
1631 					sdp->sd_flags |= FLG_SY_SPECSEC;
1632 				else
1633 					sdp->sd_flags &= ~FLG_SY_SPECSEC;
1634 				break;
1635 			case SDAUX_ID_END:
1636 				sym->st_value = end;
1637 				sectndx = end_ndx;
1638 				if (end_abs)
1639 					sdp->sd_flags |= FLG_SY_SPECSEC;
1640 				else
1641 					sdp->sd_flags &= ~FLG_SY_SPECSEC;
1642 				break;
1643 			case SDAUX_ID_START:
1644 				sym->st_value = start;
1645 				sectndx = start_ndx;
1646 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1647 				break;
1648 			case SDAUX_ID_DYN:
1649 				if (flags & FLG_OF_DYNAMIC) {
1650 					sym->st_value = ofl->
1651 					    ofl_osdynamic->os_shdr->sh_addr;
1652 					/* LINTED */
1653 					sectndx = elf_ndxscn(
1654 					    ofl->ofl_osdynamic->os_scn);
1655 					sdp->sd_flags &= ~FLG_SY_SPECSEC;
1656 				}
1657 				break;
1658 			case SDAUX_ID_PLT:
1659 				if (ofl->ofl_osplt) {
1660 					sym->st_value = ofl->
1661 					    ofl_osplt->os_shdr->sh_addr;
1662 					/* LINTED */
1663 					sectndx = elf_ndxscn(
1664 					    ofl->ofl_osplt->os_scn);
1665 					sdp->sd_flags &= ~FLG_SY_SPECSEC;
1666 				}
1667 				break;
1668 			case SDAUX_ID_GOT:
1669 				/*
1670 				 * Symbol bias for negative growing tables is
1671 				 * stored in symbol's value during
1672 				 * allocate_got().
1673 				 */
1674 				sym->st_value += ofl->
1675 				    ofl_osgot->os_shdr->sh_addr;
1676 				/* LINTED */
1677 				sectndx = elf_ndxscn(ofl->
1678 				    ofl_osgot->os_scn);
1679 				sdp->sd_flags &= ~FLG_SY_SPECSEC;
1680 				break;
1681 			default:
1682 				/* NOTHING */
1683 				;
1684 			}
1685 		}
1686 
1687 		/*
1688 		 * If a plt index has been assigned to an undefined function,
1689 		 * update the symbols value to the appropriate .plt address.
1690 		 */
1691 		if ((flags & FLG_OF_DYNAMIC) && (flags & FLG_OF_EXEC) &&
1692 		    (sdp->sd_file) &&
1693 		    (sdp->sd_file->ifl_ehdr->e_type == ET_DYN) &&
1694 		    (ELF_ST_TYPE(sym->st_info) == STT_FUNC) &&
1695 		    !(flags & FLG_OF_BFLAG)) {
1696 			if (sap->sa_PLTndx)
1697 				sym->st_value =
1698 				    (*ld_targ.t_mr.mr_calc_plt_addr)(sdp, ofl);
1699 		}
1700 
1701 		/*
1702 		 * Finish updating the symbols.
1703 		 */
1704 
1705 		/*
1706 		 * Sym Update: if scoped local - set local binding
1707 		 */
1708 		if (local)
1709 			sym->st_info = ELF_ST_INFO(STB_LOCAL,
1710 			    ELF_ST_TYPE(sym->st_info));
1711 
1712 		/*
1713 		 * Sym Updated: If both the .symtab and .dynsym
1714 		 * are present then we've actually updated the information in
1715 		 * the .dynsym, therefore copy this same information to the
1716 		 * .symtab entry.
1717 		 */
1718 		sdp->sd_shndx = sectndx;
1719 		if (enter_in_symtab && dynsym && (!local || dynlocal)) {
1720 			Word _symndx = dynlocal ? scopesym_ndx : symtab_ndx;
1721 
1722 			symtab[_symndx].st_value = sym->st_value;
1723 			symtab[_symndx].st_size = sym->st_size;
1724 			symtab[_symndx].st_info = sym->st_info;
1725 			symtab[_symndx].st_other = sym->st_other;
1726 		}
1727 
1728 
1729 		if (enter_in_symtab) {
1730 			Word	_symndx;
1731 
1732 			if (local)
1733 				_symndx = scopesym_ndx++;
1734 			else
1735 				_symndx = symtab_ndx++;
1736 			if (((sdp->sd_flags & FLG_SY_SPECSEC) == 0) &&
1737 			    (sectndx >= SHN_LORESERVE)) {
1738 				assert(symshndx != 0);
1739 				symshndx[_symndx] = sectndx;
1740 				symtab[_symndx].st_shndx = SHN_XINDEX;
1741 			} else {
1742 				/* LINTED */
1743 				symtab[_symndx].st_shndx = (Half)sectndx;
1744 			}
1745 		}
1746 
1747 		if (dynsym && (!local || dynlocal)) {
1748 			/*
1749 			 * dynsym and ldynsym are distinct tables, so
1750 			 * we use indirection to access the right one
1751 			 * and the related extended section index array.
1752 			 */
1753 			Word	_symndx;
1754 			Sym	*_dynsym;
1755 			Word	*_dynshndx;
1756 
1757 			if (!local) {
1758 				_symndx = dynsym_ndx++;
1759 				_dynsym = dynsym;
1760 				_dynshndx = dynshndx;
1761 			} else {
1762 				_symndx = ldynscopesym_ndx++;
1763 				_dynsym = ldynsym;
1764 				_dynshndx = ldynshndx;
1765 			}
1766 			if (((sdp->sd_flags & FLG_SY_SPECSEC) == 0) &&
1767 			    (sectndx >= SHN_LORESERVE)) {
1768 				assert(_dynshndx != 0);
1769 				_dynshndx[_symndx] = sectndx;
1770 				_dynsym[_symndx].st_shndx = SHN_XINDEX;
1771 			} else {
1772 				/* LINTED */
1773 				_dynsym[_symndx].st_shndx = (Half)sectndx;
1774 			}
1775 		}
1776 
1777 		DBG_CALL(Dbg_syms_new(ofl, sym, sdp));
1778 	}
1779 
1780 	/*
1781 	 * Now that all the symbols have been processed update any weak symbols
1782 	 * information (ie. copy all information except `st_name').  As both
1783 	 * symbols will be represented in the output, return the weak symbol to
1784 	 * its correct type.
1785 	 */
1786 	for (LIST_TRAVERSE(&weak, lnp1, wkp)) {
1787 		Sym_desc *	sdp, * _sdp;
1788 		Sym *		sym, * _sym, * __sym;
1789 		uchar_t		bind;
1790 
1791 		sdp = wkp->wk_weak;
1792 		_sdp = wkp->wk_alias;
1793 		_sym = _sdp->sd_sym;
1794 
1795 		sdp->sd_flags |= FLG_SY_WEAKDEF;
1796 
1797 		/*
1798 		 * If the symbol definition has been scoped then assign it to
1799 		 * be local, otherwise if it's from a shared object then we need
1800 		 * to maintain the binding of the original reference.
1801 		 */
1802 		if (sdp->sd_flags1 & FLG_SY1_HIDDEN) {
1803 			if (flags & FLG_OF_PROCRED)
1804 				bind = STB_LOCAL;
1805 			else
1806 				bind = STB_WEAK;
1807 		} else if ((sdp->sd_ref == REF_DYN_NEED) &&
1808 		    (sdp->sd_flags & FLG_SY_GLOBREF))
1809 			bind = STB_GLOBAL;
1810 		else
1811 			bind = STB_WEAK;
1812 
1813 		DBG_CALL(Dbg_syms_old(ofl, sdp));
1814 		if ((sym = wkp->wk_symtab) != 0) {
1815 			sym = wkp->wk_symtab;
1816 			sym->st_value = _sym->st_value;
1817 			sym->st_size = _sym->st_size;
1818 			sym->st_other = _sym->st_other;
1819 			sym->st_shndx = _sym->st_shndx;
1820 			sym->st_info = ELF_ST_INFO(bind,
1821 			    ELF_ST_TYPE(sym->st_info));
1822 			__sym = sym;
1823 		}
1824 		if ((sym = wkp->wk_dynsym) != 0) {
1825 			sym = wkp->wk_dynsym;
1826 			sym->st_value = _sym->st_value;
1827 			sym->st_size = _sym->st_size;
1828 			sym->st_other = _sym->st_other;
1829 			sym->st_shndx = _sym->st_shndx;
1830 			sym->st_info = ELF_ST_INFO(bind,
1831 			    ELF_ST_TYPE(sym->st_info));
1832 			__sym = sym;
1833 		}
1834 		DBG_CALL(Dbg_syms_new(ofl, __sym, sdp));
1835 	}
1836 
1837 	/*
1838 	 * Now display GOT debugging information if required.
1839 	 */
1840 	DBG_CALL(Dbg_got_display(ofl, 0, 0,
1841 	    ld_targ.t_m.m_got_xnumber, ld_targ.t_m.m_got_entsize));
1842 
1843 	/*
1844 	 * Update the section headers information. sh_info is
1845 	 * supposed to contain the offset at which the first
1846 	 * global symbol resides in the symbol table, while
1847 	 * sh_link contains the section index of the associated
1848 	 * string table.
1849 	 */
1850 	if (symtab) {
1851 		Shdr	*shdr = ofl->ofl_ossymtab->os_shdr;
1852 
1853 		shdr->sh_info = ofl->ofl_shdrcnt + ofl->ofl_locscnt +
1854 		    ofl->ofl_scopecnt + 2;
1855 		/* LINTED */
1856 		shdr->sh_link = (Word)elf_ndxscn(ofl->ofl_osstrtab->os_scn);
1857 		if (symshndx) {
1858 			shdr = ofl->ofl_ossymshndx->os_shdr;
1859 			shdr->sh_link =
1860 			    (Word)elf_ndxscn(ofl->ofl_ossymtab->os_scn);
1861 		}
1862 	}
1863 	if (dynsym) {
1864 		Shdr	*shdr = ofl->ofl_osdynsym->os_shdr;
1865 
1866 		shdr->sh_info = 1 + ofl->ofl_dynshdrcnt + ofl->ofl_lregsymcnt;
1867 		/* LINTED */
1868 		shdr->sh_link = (Word)elf_ndxscn(ofl->ofl_osdynstr->os_scn);
1869 
1870 		ofl->ofl_oshash->os_shdr->sh_link =
1871 		    /* LINTED */
1872 		    (Word)elf_ndxscn(ofl->ofl_osdynsym->os_scn);
1873 		if (dynshndx) {
1874 			shdr = ofl->ofl_osdynshndx->os_shdr;
1875 			shdr->sh_link =
1876 			    (Word)elf_ndxscn(ofl->ofl_osdynsym->os_scn);
1877 		}
1878 	}
1879 	if (ldynsym) {
1880 		Shdr	*shdr = ofl->ofl_osldynsym->os_shdr;
1881 
1882 		/* ldynsym has no globals, so give index one past the end */
1883 		shdr->sh_info = ldynsym_ndx;
1884 
1885 		/*
1886 		 * The ldynsym and dynsym must be adjacent. The
1887 		 * idea is that rtld should be able to start with
1888 		 * the ldynsym and march straight through the end
1889 		 * of dynsym, seeing them as a single symbol table,
1890 		 * despite the fact that they are in distinct sections.
1891 		 * Ensure that this happened correctly.
1892 		 *
1893 		 * Note that I use ldynsym_ndx here instead of the
1894 		 * computation I used to set the section size
1895 		 * (found in ldynsym_cnt). The two will agree, unless
1896 		 * we somehow miscounted symbols or failed to insert them
1897 		 * all. Using ldynsym_ndx here catches that error in
1898 		 * addition to checking for adjacency.
1899 		 */
1900 		assert(dynsym == (ldynsym + ldynsym_ndx));
1901 
1902 
1903 		/* LINTED */
1904 		shdr->sh_link = (Word)elf_ndxscn(ofl->ofl_osdynstr->os_scn);
1905 
1906 		if (ldynshndx) {
1907 			shdr = ofl->ofl_osldynshndx->os_shdr;
1908 			shdr->sh_link =
1909 			    (Word)elf_ndxscn(ofl->ofl_osldynsym->os_scn);
1910 		}
1911 
1912 		/*
1913 		 * The presence of .SUNW_ldynsym means that there may be
1914 		 * associated sort sections, one for regular symbols
1915 		 * and the other for TLS. Each sort section needs the
1916 		 * following done:
1917 		 *	- Section header link references .SUNW_ldynsym
1918 		 *	- Should have received the expected # of items
1919 		 *	- Sorted by increasing address
1920 		 */
1921 		if (ofl->ofl_osdynsymsort) {	/* .SUNW_dynsymsort */
1922 			ofl->ofl_osdynsymsort->os_shdr->sh_link =
1923 			    (Word)elf_ndxscn(ofl->ofl_osldynsym->os_scn);
1924 			assert(ofl->ofl_dynsymsortcnt == dynsymsort_ndx);
1925 
1926 			if (dynsymsort_ndx > 1) {
1927 				dynsort_compare_syms = ldynsym;
1928 				qsort(dynsymsort, dynsymsort_ndx,
1929 				    sizeof (*dynsymsort), dynsort_compare);
1930 				dynsort_dupwarn(ofl, ldynsym,
1931 				    st_getstrbuf(dynstr),
1932 				    dynsymsort, dynsymsort_ndx,
1933 				    MSG_ORIG(MSG_SCN_DYNSYMSORT));
1934 			}
1935 		}
1936 		if (ofl->ofl_osdyntlssort) {	/* .SUNW_dyntlssort */
1937 			ofl->ofl_osdyntlssort->os_shdr->sh_link =
1938 			    (Word)elf_ndxscn(ofl->ofl_osldynsym->os_scn);
1939 			assert(ofl->ofl_dyntlssortcnt == dyntlssort_ndx);
1940 
1941 			if (dyntlssort_ndx > 1) {
1942 				dynsort_compare_syms = ldynsym;
1943 				qsort(dyntlssort, dyntlssort_ndx,
1944 				    sizeof (*dyntlssort), dynsort_compare);
1945 				dynsort_dupwarn(ofl, ldynsym,
1946 				    st_getstrbuf(dynstr),
1947 				    dyntlssort, dyntlssort_ndx,
1948 				    MSG_ORIG(MSG_SCN_DYNTLSSORT));
1949 			}
1950 		}
1951 	}
1952 
1953 	/*
1954 	 * Used by ld.so.1 only.
1955 	 */
1956 	return (etext);
1957 
1958 #undef ADD_TO_DYNSORT
1959 }
1960 
1961 /*
1962  * Build the dynamic section.
1963  *
1964  * This routine must be maintained in parallel with make_dynamic()
1965  * in sections.c
1966  */
1967 static int
1968 update_odynamic(Ofl_desc *ofl)
1969 {
1970 	Listnode	*lnp;
1971 	Ifl_desc	*ifl;
1972 	Sym_desc	*sdp;
1973 	Shdr		*shdr;
1974 	Dyn		*_dyn = (Dyn *)ofl->ofl_osdynamic->os_outdata->d_buf;
1975 	Dyn		*dyn;
1976 	Str_tbl		*dynstr;
1977 	size_t		stoff;
1978 	ofl_flag_t	flags = ofl->ofl_flags;
1979 	int		not_relobj = !(flags & FLG_OF_RELOBJ);
1980 	Word		cnt;
1981 
1982 
1983 	/*
1984 	 * A relocatable object with a dynamic section is possible, though
1985 	 * rare. One use for this feature is to produce drivers
1986 	 * for the kernel, loaded by krtld.
1987 	 *
1988 	 * Only a limited subset of DT_ entries apply to relocatable
1989 	 * objects:
1990 	 *
1991 	 *	DT_NEEDED
1992 	 *	DT_RUNPATH/DT_RPATH
1993 	 *	DT_FLAGS
1994 	 *	DT_FLAGS1
1995 	 *	DT_SUNW_STRPAD
1996 	 *	DT_LDMACH
1997 	 */
1998 
1999 	dynstr = ofl->ofl_dynstrtab;
2000 	ofl->ofl_osdynamic->os_shdr->sh_link =
2001 	    /* LINTED */
2002 	    (Word)elf_ndxscn(ofl->ofl_osdynstr->os_scn);
2003 
2004 	dyn = _dyn;
2005 
2006 	for (LIST_TRAVERSE(&ofl->ofl_sos, lnp, ifl)) {
2007 		if ((ifl->ifl_flags &
2008 		    (FLG_IF_IGNORE | FLG_IF_DEPREQD)) == FLG_IF_IGNORE)
2009 			continue;
2010 
2011 		/*
2012 		 * Create and set up the DT_POSFLAG_1 entry here if required.
2013 		 */
2014 		if ((ifl->ifl_flags & (FLG_IF_LAZYLD|FLG_IF_GRPPRM)) &&
2015 		    (ifl->ifl_flags & (FLG_IF_NEEDED)) && not_relobj) {
2016 			dyn->d_tag = DT_POSFLAG_1;
2017 			if (ifl->ifl_flags & FLG_IF_LAZYLD)
2018 				dyn->d_un.d_val = DF_P1_LAZYLOAD;
2019 			if (ifl->ifl_flags & FLG_IF_GRPPRM)
2020 				dyn->d_un.d_val |= DF_P1_GROUPPERM;
2021 			dyn++;
2022 		}
2023 
2024 		if (ifl->ifl_flags & (FLG_IF_NEEDED | FLG_IF_NEEDSTR))
2025 			dyn->d_tag = DT_NEEDED;
2026 		else
2027 			continue;
2028 
2029 		(void) st_setstring(dynstr, ifl->ifl_soname, &stoff);
2030 		dyn->d_un.d_val = stoff;
2031 		/* LINTED */
2032 		ifl->ifl_neededndx = (Half)(((uintptr_t)dyn - (uintptr_t)_dyn) /
2033 		    sizeof (Dyn));
2034 		dyn++;
2035 	}
2036 
2037 	if (not_relobj) {
2038 		if (ofl->ofl_dtsfltrs != NULL) {
2039 			Dfltr_desc	*dftp;
2040 			Aliste		idx;
2041 
2042 			for (ALIST_TRAVERSE(ofl->ofl_dtsfltrs, idx, dftp)) {
2043 				if (dftp->dft_flag == FLG_SY_AUXFLTR)
2044 					dyn->d_tag = DT_SUNW_AUXILIARY;
2045 				else
2046 					dyn->d_tag = DT_SUNW_FILTER;
2047 
2048 				(void) st_setstring(dynstr, dftp->dft_str,
2049 				    &stoff);
2050 				dyn->d_un.d_val = stoff;
2051 				dftp->dft_ndx = (Half)(((uintptr_t)dyn -
2052 				    (uintptr_t)_dyn) / sizeof (Dyn));
2053 				dyn++;
2054 			}
2055 		}
2056 		if (((sdp = ld_sym_find(MSG_ORIG(MSG_SYM_INIT_U),
2057 		    SYM_NOHASH, 0, ofl)) != NULL) &&
2058 		    (sdp->sd_ref == REF_REL_NEED) &&
2059 		    (sdp->sd_sym->st_shndx != SHN_UNDEF)) {
2060 			dyn->d_tag = DT_INIT;
2061 			dyn->d_un.d_ptr = sdp->sd_sym->st_value;
2062 			dyn++;
2063 		}
2064 		if (((sdp = ld_sym_find(MSG_ORIG(MSG_SYM_FINI_U),
2065 		    SYM_NOHASH, 0, ofl)) != NULL) &&
2066 		    (sdp->sd_ref == REF_REL_NEED) &&
2067 		    (sdp->sd_sym->st_shndx != SHN_UNDEF)) {
2068 			dyn->d_tag = DT_FINI;
2069 			dyn->d_un.d_ptr = sdp->sd_sym->st_value;
2070 			dyn++;
2071 		}
2072 		if (ofl->ofl_soname) {
2073 			dyn->d_tag = DT_SONAME;
2074 			(void) st_setstring(dynstr, ofl->ofl_soname, &stoff);
2075 			dyn->d_un.d_val = stoff;
2076 			dyn++;
2077 		}
2078 		if (ofl->ofl_filtees) {
2079 			if (flags & FLG_OF_AUX) {
2080 				dyn->d_tag = DT_AUXILIARY;
2081 			} else {
2082 				dyn->d_tag = DT_FILTER;
2083 			}
2084 			(void) st_setstring(dynstr, ofl->ofl_filtees, &stoff);
2085 			dyn->d_un.d_val = stoff;
2086 			dyn++;
2087 		}
2088 	}
2089 
2090 	if (ofl->ofl_rpath) {
2091 		(void) st_setstring(dynstr, ofl->ofl_rpath, &stoff);
2092 		dyn->d_tag = DT_RUNPATH;
2093 		dyn->d_un.d_val = stoff;
2094 		dyn++;
2095 		dyn->d_tag = DT_RPATH;
2096 		dyn->d_un.d_val = stoff;
2097 		dyn++;
2098 	}
2099 
2100 	if (not_relobj) {
2101 		if (ofl->ofl_config) {
2102 			dyn->d_tag = DT_CONFIG;
2103 			(void) st_setstring(dynstr, ofl->ofl_config, &stoff);
2104 			dyn->d_un.d_val = stoff;
2105 			dyn++;
2106 		}
2107 		if (ofl->ofl_depaudit) {
2108 			dyn->d_tag = DT_DEPAUDIT;
2109 			(void) st_setstring(dynstr, ofl->ofl_depaudit, &stoff);
2110 			dyn->d_un.d_val = stoff;
2111 			dyn++;
2112 		}
2113 		if (ofl->ofl_audit) {
2114 			dyn->d_tag = DT_AUDIT;
2115 			(void) st_setstring(dynstr, ofl->ofl_audit, &stoff);
2116 			dyn->d_un.d_val = stoff;
2117 			dyn++;
2118 		}
2119 
2120 		dyn->d_tag = DT_HASH;
2121 		dyn->d_un.d_ptr = ofl->ofl_oshash->os_shdr->sh_addr;
2122 		dyn++;
2123 
2124 		shdr = ofl->ofl_osdynstr->os_shdr;
2125 		dyn->d_tag = DT_STRTAB;
2126 		dyn->d_un.d_ptr = shdr->sh_addr;
2127 		dyn++;
2128 
2129 		dyn->d_tag = DT_STRSZ;
2130 		dyn->d_un.d_ptr = shdr->sh_size;
2131 		dyn++;
2132 
2133 		shdr = ofl->ofl_osdynsym->os_shdr;
2134 		dyn->d_tag = DT_SYMTAB;
2135 		dyn->d_un.d_ptr = shdr->sh_addr;
2136 		dyn++;
2137 
2138 		dyn->d_tag = DT_SYMENT;
2139 		dyn->d_un.d_ptr = shdr->sh_entsize;
2140 		dyn++;
2141 
2142 		if (ofl->ofl_osldynsym) {
2143 			/*
2144 			 * We have arranged for the .SUNW_ldynsym data to be
2145 			 * immediately in front of the .dynsym data.
2146 			 * This means that you could start at the top
2147 			 * of .SUNW_ldynsym and see the data for both tables
2148 			 * without a break. This is the view we want to
2149 			 * provide for DT_SUNW_SYMTAB, which is why we
2150 			 * add the lengths together.
2151 			 */
2152 			Shdr *lshdr = ofl->ofl_osldynsym->os_shdr;
2153 			dyn->d_tag = DT_SUNW_SYMTAB;
2154 			dyn->d_un.d_ptr = lshdr->sh_addr;
2155 			dyn++;
2156 
2157 			dyn->d_tag = DT_SUNW_SYMSZ;
2158 			dyn->d_un.d_val = lshdr->sh_size + shdr->sh_size;
2159 			dyn++;
2160 		}
2161 
2162 		if (ofl->ofl_osdynsymsort || ofl->ofl_osdyntlssort) {
2163 			dyn->d_tag = DT_SUNW_SORTENT;
2164 			dyn->d_un.d_val = sizeof (Word);
2165 			dyn++;
2166 		}
2167 
2168 		if (ofl->ofl_osdynsymsort) {
2169 			dyn->d_tag = DT_SUNW_SYMSORT;
2170 			dyn->d_un.d_ptr =
2171 			    ofl->ofl_osdynsymsort->os_shdr->sh_addr;
2172 			dyn++;
2173 
2174 			dyn->d_tag = DT_SUNW_SYMSORTSZ;
2175 			dyn->d_un.d_val =
2176 			    ofl->ofl_osdynsymsort->os_shdr->sh_size;
2177 			dyn++;
2178 		}
2179 
2180 		if (ofl->ofl_osdyntlssort) {
2181 			dyn->d_tag = DT_SUNW_TLSSORT;
2182 			dyn->d_un.d_ptr =
2183 			    ofl->ofl_osdyntlssort->os_shdr->sh_addr;
2184 			dyn++;
2185 
2186 			dyn->d_tag = DT_SUNW_TLSSORTSZ;
2187 			dyn->d_un.d_val =
2188 			    ofl->ofl_osdyntlssort->os_shdr->sh_size;
2189 			dyn++;
2190 		}
2191 
2192 		/*
2193 		 * Reserve the DT_CHECKSUM entry.  Its value will be filled in
2194 		 * after the complete image is built.
2195 		 */
2196 		dyn->d_tag = DT_CHECKSUM;
2197 		ofl->ofl_checksum = &dyn->d_un.d_val;
2198 		dyn++;
2199 
2200 		/*
2201 		 * Versioning sections: DT_VERDEF and DT_VERNEED.
2202 		 *
2203 		 * The Solaris ld does not produce DT_VERSYM, but the GNU ld
2204 		 * does, in order to support their style of versioning, which
2205 		 * differs from ours:
2206 		 *
2207 		 *	- The top bit of the 16-bit Versym index is
2208 		 *		not part of the version, but is interpreted
2209 		 *		as a "hidden bit".
2210 		 *
2211 		 *	- External (SHN_UNDEF) symbols can have non-zero
2212 		 *		Versym values, which specify versions in
2213 		 *		referenced objects, via the Verneed section.
2214 		 *
2215 		 *	- The vna_other field of the Vernaux structures
2216 		 *		found in the Verneed section are not zero as
2217 		 *		with Solaris, but instead contain the version
2218 		 *		index to be used by Versym indices to reference
2219 		 *		the given external version.
2220 		 *
2221 		 * The Solaris ld, rtld, and elfdump programs all interpret the
2222 		 * presence of DT_VERSYM as meaning that GNU versioning rules
2223 		 * apply to the given file. If DT_VERSYM is not present,
2224 		 * then Solaris versioning rules apply. If we should ever need
2225 		 * to change our ld so that it does issue DT_VERSYM, then
2226 		 * this rule for detecting GNU versioning will no longer work.
2227 		 * In that case, we will have to invent a way to explicitly
2228 		 * specify the style of versioning in use, perhaps via a
2229 		 * new dynamic entry named something like DT_SUNW_VERSIONSTYLE,
2230 		 * where the d_un.d_val value specifies which style is to be
2231 		 * used.
2232 		 */
2233 		if ((flags & (FLG_OF_VERDEF | FLG_OF_NOVERSEC)) ==
2234 		    FLG_OF_VERDEF) {
2235 			shdr = ofl->ofl_osverdef->os_shdr;
2236 			dyn->d_tag = DT_VERDEF;
2237 			dyn->d_un.d_ptr = shdr->sh_addr;
2238 			dyn++;
2239 			dyn->d_tag = DT_VERDEFNUM;
2240 			dyn->d_un.d_ptr = shdr->sh_info;
2241 			dyn++;
2242 		}
2243 		if ((flags & (FLG_OF_VERNEED | FLG_OF_NOVERSEC)) ==
2244 		    FLG_OF_VERNEED) {
2245 			shdr = ofl->ofl_osverneed->os_shdr;
2246 			dyn->d_tag = DT_VERNEED;
2247 			dyn->d_un.d_ptr = shdr->sh_addr;
2248 			dyn++;
2249 			dyn->d_tag = DT_VERNEEDNUM;
2250 			dyn->d_un.d_ptr = shdr->sh_info;
2251 			dyn++;
2252 		}
2253 
2254 		if ((flags & FLG_OF_COMREL) && ofl->ofl_relocrelcnt) {
2255 			dyn->d_tag = ld_targ.t_m.m_rel_dt_count;
2256 			dyn->d_un.d_val = ofl->ofl_relocrelcnt;
2257 			dyn++;
2258 		}
2259 		if (flags & FLG_OF_TEXTREL) {
2260 			/*
2261 			 * Only the presence of this entry is used in this
2262 			 * implementation, not the value stored.
2263 			 */
2264 			dyn->d_tag = DT_TEXTREL;
2265 			dyn->d_un.d_val = 0;
2266 			dyn++;
2267 		}
2268 
2269 		if (ofl->ofl_osfiniarray) {
2270 			shdr = ofl->ofl_osfiniarray->os_shdr;
2271 
2272 			dyn->d_tag = DT_FINI_ARRAY;
2273 			dyn->d_un.d_ptr = shdr->sh_addr;
2274 			dyn++;
2275 
2276 			dyn->d_tag = DT_FINI_ARRAYSZ;
2277 			dyn->d_un.d_val = shdr->sh_size;
2278 			dyn++;
2279 		}
2280 
2281 		if (ofl->ofl_osinitarray) {
2282 			shdr = ofl->ofl_osinitarray->os_shdr;
2283 
2284 			dyn->d_tag = DT_INIT_ARRAY;
2285 			dyn->d_un.d_ptr = shdr->sh_addr;
2286 			dyn++;
2287 
2288 			dyn->d_tag = DT_INIT_ARRAYSZ;
2289 			dyn->d_un.d_val = shdr->sh_size;
2290 			dyn++;
2291 		}
2292 
2293 		if (ofl->ofl_ospreinitarray) {
2294 			shdr = ofl->ofl_ospreinitarray->os_shdr;
2295 
2296 			dyn->d_tag = DT_PREINIT_ARRAY;
2297 			dyn->d_un.d_ptr = shdr->sh_addr;
2298 			dyn++;
2299 
2300 			dyn->d_tag = DT_PREINIT_ARRAYSZ;
2301 			dyn->d_un.d_val = shdr->sh_size;
2302 			dyn++;
2303 		}
2304 
2305 		if (ofl->ofl_pltcnt) {
2306 			shdr =  ofl->ofl_osplt->os_relosdesc->os_shdr;
2307 
2308 			dyn->d_tag = DT_PLTRELSZ;
2309 			dyn->d_un.d_ptr = shdr->sh_size;
2310 			dyn++;
2311 			dyn->d_tag = DT_PLTREL;
2312 			dyn->d_un.d_ptr = ld_targ.t_m.m_rel_dt_type;
2313 			dyn++;
2314 			dyn->d_tag = DT_JMPREL;
2315 			dyn->d_un.d_ptr = shdr->sh_addr;
2316 			dyn++;
2317 		}
2318 		if (ofl->ofl_pltpad) {
2319 			shdr =  ofl->ofl_osplt->os_shdr;
2320 
2321 			dyn->d_tag = DT_PLTPAD;
2322 			if (ofl->ofl_pltcnt) {
2323 				dyn->d_un.d_ptr = shdr->sh_addr +
2324 				    ld_targ.t_m.m_plt_reservsz +
2325 				    ofl->ofl_pltcnt * ld_targ.t_m.m_plt_entsize;
2326 			} else
2327 				dyn->d_un.d_ptr = shdr->sh_addr;
2328 			dyn++;
2329 			dyn->d_tag = DT_PLTPADSZ;
2330 			dyn->d_un.d_val = ofl->ofl_pltpad *
2331 			    ld_targ.t_m.m_plt_entsize;
2332 			dyn++;
2333 		}
2334 		if (ofl->ofl_relocsz) {
2335 			dyn->d_tag = ld_targ.t_m.m_rel_dt_type;
2336 			dyn->d_un.d_ptr = ofl->ofl_osrelhead->os_shdr->sh_addr;
2337 			dyn++;
2338 			dyn->d_tag = ld_targ.t_m.m_rel_dt_size;
2339 			dyn->d_un.d_ptr = ofl->ofl_relocsz;
2340 			dyn++;
2341 			dyn->d_tag = ld_targ.t_m.m_rel_dt_ent;
2342 			if (ofl->ofl_osrelhead->os_shdr->sh_type == SHT_REL)
2343 				dyn->d_un.d_ptr = sizeof (Rel);
2344 			else
2345 				dyn->d_un.d_ptr = sizeof (Rela);
2346 			dyn++;
2347 		}
2348 		if (ofl->ofl_ossyminfo) {
2349 			shdr = ofl->ofl_ossyminfo->os_shdr;
2350 			dyn->d_tag = DT_SYMINFO;
2351 			dyn->d_un.d_ptr = shdr->sh_addr;
2352 			dyn++;
2353 			dyn->d_tag = DT_SYMINSZ;
2354 			dyn->d_un.d_val = shdr->sh_size;
2355 			dyn++;
2356 			dyn->d_tag = DT_SYMINENT;
2357 			dyn->d_un.d_val = sizeof (Syminfo);
2358 			dyn++;
2359 		}
2360 		if (ofl->ofl_osmove) {
2361 			Os_desc *	osp;
2362 
2363 			dyn->d_tag = DT_MOVEENT;
2364 			osp = ofl->ofl_osmove;
2365 			dyn->d_un.d_val = osp->os_shdr->sh_entsize;
2366 			dyn++;
2367 			dyn->d_tag = DT_MOVESZ;
2368 			dyn->d_un.d_val = osp->os_shdr->sh_size;
2369 			dyn++;
2370 			dyn->d_tag = DT_MOVETAB;
2371 			dyn->d_un.d_val = osp->os_shdr->sh_addr;
2372 			dyn++;
2373 		}
2374 		if (ofl->ofl_regsymcnt) {
2375 			int	ndx;
2376 
2377 			for (ndx = 0; ndx < ofl->ofl_regsymsno; ndx++) {
2378 				if ((sdp = ofl->ofl_regsyms[ndx]) == 0)
2379 					continue;
2380 
2381 				dyn->d_tag = ld_targ.t_m.m_dt_register;
2382 				dyn->d_un.d_val = sdp->sd_symndx;
2383 				dyn++;
2384 			}
2385 		}
2386 
2387 		for (LIST_TRAVERSE(&ofl->ofl_rtldinfo, lnp, sdp)) {
2388 			dyn->d_tag = DT_SUNW_RTLDINF;
2389 			dyn->d_un.d_ptr = sdp->sd_sym->st_value;
2390 			dyn++;
2391 		}
2392 
2393 		if (ofl->ofl_osdynamic->os_sgdesc &&
2394 		    (ofl->ofl_osdynamic->os_sgdesc->sg_phdr.p_flags & PF_W)) {
2395 			if (ofl->ofl_osinterp) {
2396 				dyn->d_tag = DT_DEBUG;
2397 				dyn->d_un.d_ptr = 0;
2398 				dyn++;
2399 			}
2400 
2401 			dyn->d_tag = DT_FEATURE_1;
2402 			if (ofl->ofl_osmove)
2403 				dyn->d_un.d_val = 0;
2404 			else
2405 				dyn->d_un.d_val = DTF_1_PARINIT;
2406 			dyn++;
2407 		}
2408 
2409 		if (ofl->ofl_oscap) {
2410 			dyn->d_tag = DT_SUNW_CAP;
2411 			dyn->d_un.d_val = ofl->ofl_oscap->os_shdr->sh_addr;
2412 			dyn++;
2413 		}
2414 
2415 		if (flags & FLG_OF_SYMBOLIC) {
2416 			dyn->d_tag = DT_SYMBOLIC;
2417 			dyn->d_un.d_val = 0;
2418 			dyn++;
2419 		}
2420 	}
2421 
2422 	dyn->d_tag = DT_FLAGS;
2423 	dyn->d_un.d_val = ofl->ofl_dtflags;
2424 	dyn++;
2425 
2426 	/*
2427 	 * If -Bdirect was specified, but some NODIRECT symbols were specified
2428 	 * via a mapfile, or -znodirect was used on the command line, then
2429 	 * clear the DF_1_DIRECT flag.  The resultant object will use per-symbol
2430 	 * direct bindings rather than be enabled for global direct bindings.
2431 	 */
2432 	if (ofl->ofl_flags1 & FLG_OF1_NDIRECT) {
2433 		ofl->ofl_dtflags_1 &= ~DF_1_DIRECT;
2434 		ofl->ofl_dtflags_1 |= DF_1_NODIRECT;
2435 	}
2436 
2437 	dyn->d_tag = DT_FLAGS_1;
2438 	dyn->d_un.d_val = ofl->ofl_dtflags_1;
2439 	dyn++;
2440 
2441 	dyn->d_tag = DT_SUNW_STRPAD;
2442 	dyn->d_un.d_val = DYNSTR_EXTRA_PAD;
2443 	dyn++;
2444 
2445 	dyn->d_tag = DT_SUNW_LDMACH;
2446 	dyn->d_un.d_val = ld_sunw_ldmach();
2447 	dyn++;
2448 
2449 	(*ld_targ.t_mr.mr_mach_update_odynamic)(ofl, &dyn);
2450 
2451 	for (cnt = 1 + DYNAMIC_EXTRA_ELTS; cnt--; dyn++) {
2452 		dyn->d_tag = DT_NULL;
2453 		dyn->d_un.d_val = 0;
2454 	}
2455 
2456 	/*
2457 	 * Ensure that we wrote the right number of entries. If not,
2458 	 * we either miscounted in make_dynamic(), or we did something wrong
2459 	 * in this function.
2460 	 */
2461 	assert((ofl->ofl_osdynamic->os_shdr->sh_size /
2462 	    ofl->ofl_osdynamic->os_shdr->sh_entsize) ==
2463 	    ((uintptr_t)dyn - (uintptr_t)_dyn) / sizeof (*dyn));
2464 
2465 	return (1);
2466 }
2467 
2468 /*
2469  * Build the version definition section
2470  */
2471 static int
2472 update_overdef(Ofl_desc *ofl)
2473 {
2474 	Listnode	*lnp1, *lnp2;
2475 	Ver_desc	*vdp, *_vdp;
2476 	Verdef		*vdf, *_vdf;
2477 	int		num = 0;
2478 	Os_desc		*strosp;
2479 
2480 	/*
2481 	 * Traverse the version descriptors and update the version structures
2482 	 * to point to the dynstr name in preparation for building the version
2483 	 * section structure.
2484 	 */
2485 	for (LIST_TRAVERSE(&ofl->ofl_verdesc, lnp1, vdp)) {
2486 		Sym_desc *	sdp;
2487 
2488 		if (vdp->vd_flags & VER_FLG_BASE) {
2489 			const char	*name = vdp->vd_name;
2490 			size_t		stoff;
2491 
2492 			/*
2493 			 * Create a new string table entry to represent the base
2494 			 * version name (there is no corresponding symbol for
2495 			 * this).
2496 			 */
2497 			if (!(ofl->ofl_flags & FLG_OF_DYNAMIC)) {
2498 				(void) st_setstring(ofl->ofl_strtab,
2499 				    name, &stoff);
2500 				/* LINTED */
2501 				vdp->vd_name = (const char *)stoff;
2502 			} else {
2503 				(void) st_setstring(ofl->ofl_dynstrtab,
2504 				    name, &stoff);
2505 				/* LINTED */
2506 				vdp->vd_name = (const char *)stoff;
2507 			}
2508 		} else {
2509 			sdp = ld_sym_find(vdp->vd_name, vdp->vd_hash, 0, ofl);
2510 			/* LINTED */
2511 			vdp->vd_name = (const char *)
2512 			    (uintptr_t)sdp->sd_sym->st_name;
2513 		}
2514 	}
2515 
2516 	_vdf = vdf = (Verdef *)ofl->ofl_osverdef->os_outdata->d_buf;
2517 
2518 	/*
2519 	 * Traverse the version descriptors and update the version section to
2520 	 * reflect each version and its associated dependencies.
2521 	 */
2522 	for (LIST_TRAVERSE(&ofl->ofl_verdesc, lnp1, vdp)) {
2523 		Half		cnt = 1;
2524 		Verdaux *	vdap, * _vdap;
2525 
2526 		_vdap = vdap = (Verdaux *)(vdf + 1);
2527 
2528 		vdf->vd_version = VER_DEF_CURRENT;
2529 		vdf->vd_flags	= vdp->vd_flags & MSK_VER_USER;
2530 		vdf->vd_ndx	= vdp->vd_ndx;
2531 		vdf->vd_hash	= vdp->vd_hash;
2532 
2533 		/* LINTED */
2534 		vdap->vda_name = (uintptr_t)vdp->vd_name;
2535 		vdap++;
2536 		/* LINTED */
2537 		_vdap->vda_next = (Word)((uintptr_t)vdap - (uintptr_t)_vdap);
2538 
2539 		/*
2540 		 * Traverse this versions dependency list generating the
2541 		 * appropriate version dependency entries.
2542 		 */
2543 		for (LIST_TRAVERSE(&vdp->vd_deps, lnp2, _vdp)) {
2544 			/* LINTED */
2545 			vdap->vda_name = (uintptr_t)_vdp->vd_name;
2546 			_vdap = vdap;
2547 			vdap++, cnt++;
2548 			/* LINTED */
2549 			_vdap->vda_next = (Word)((uintptr_t)vdap -
2550 			    (uintptr_t)_vdap);
2551 		}
2552 		_vdap->vda_next = 0;
2553 
2554 		/*
2555 		 * Record the versions auxiliary array offset and the associated
2556 		 * dependency count.
2557 		 */
2558 		/* LINTED */
2559 		vdf->vd_aux = (Word)((uintptr_t)(vdf + 1) - (uintptr_t)vdf);
2560 		vdf->vd_cnt = cnt;
2561 
2562 		/*
2563 		 * Record the next versions offset and update the version
2564 		 * pointer.  Remember the previous version offset as the very
2565 		 * last structures next pointer should be null.
2566 		 */
2567 		_vdf = vdf;
2568 		vdf = (Verdef *)vdap, num++;
2569 		/* LINTED */
2570 		_vdf->vd_next = (Word)((uintptr_t)vdf - (uintptr_t)_vdf);
2571 	}
2572 	_vdf->vd_next = 0;
2573 
2574 	/*
2575 	 * Record the string table association with the version definition
2576 	 * section, and the symbol table associated with the version symbol
2577 	 * table (the actual contents of the version symbol table are filled
2578 	 * in during symbol update).
2579 	 */
2580 	if ((ofl->ofl_flags & FLG_OF_RELOBJ) ||
2581 	    (ofl->ofl_flags & FLG_OF_STATIC)) {
2582 		strosp = ofl->ofl_osstrtab;
2583 	} else {
2584 		strosp = ofl->ofl_osdynstr;
2585 	}
2586 	/* LINTED */
2587 	ofl->ofl_osverdef->os_shdr->sh_link = (Word)elf_ndxscn(strosp->os_scn);
2588 
2589 	/*
2590 	 * The version definition sections `info' field is used to indicate the
2591 	 * number of entries in this section.
2592 	 */
2593 	ofl->ofl_osverdef->os_shdr->sh_info = num;
2594 
2595 	return (1);
2596 }
2597 
2598 /*
2599  * Finish the version symbol index section
2600  */
2601 static int
2602 update_oversym(Ofl_desc *ofl)
2603 {
2604 	Os_desc		*symosp;
2605 
2606 	/*
2607 	 * Record the string table association with the version definition
2608 	 * section, and the symbol table associated with the version symbol
2609 	 * table (the actual contents of the version symbol table are filled
2610 	 * in during symbol update).
2611 	 */
2612 	if ((ofl->ofl_flags & FLG_OF_RELOBJ) ||
2613 	    (ofl->ofl_flags & FLG_OF_STATIC)) {
2614 		symosp = ofl->ofl_ossymtab;
2615 	} else {
2616 		symosp = ofl->ofl_osdynsym;
2617 	}
2618 
2619 	/* LINTED */
2620 	ofl->ofl_osversym->os_shdr->sh_link = (Word)elf_ndxscn(symosp->os_scn);
2621 
2622 	return (1);
2623 }
2624 
2625 /*
2626  * Build the version needed section
2627  */
2628 static int
2629 update_overneed(Ofl_desc *ofl)
2630 {
2631 	Listnode	*lnp;
2632 	Ifl_desc	*ifl;
2633 	Verneed		*vnd, *_vnd;
2634 	Str_tbl		*dynstr;
2635 	Word		num = 0;
2636 	int		has_specver;
2637 
2638 	dynstr = ofl->ofl_dynstrtab;
2639 	_vnd = vnd = (Verneed *)ofl->ofl_osverneed->os_outdata->d_buf;
2640 
2641 	/*
2642 	 * Traverse the shared object list looking for dependencies that have
2643 	 * versions defined within them.
2644 	 */
2645 	for (LIST_TRAVERSE(&ofl->ofl_sos, lnp, ifl)) {
2646 		Half		_cnt;
2647 		Word		cnt = 0;
2648 		Vernaux		*_vnap, *vnap;
2649 		Sdf_desc	*sdf = ifl->ifl_sdfdesc;
2650 		size_t		stoff;
2651 
2652 		if (!(ifl->ifl_flags & FLG_IF_VERNEED))
2653 			continue;
2654 
2655 		vnd->vn_version = VER_NEED_CURRENT;
2656 
2657 		(void) st_setstring(dynstr, ifl->ifl_soname, &stoff);
2658 		vnd->vn_file = stoff;
2659 
2660 		_vnap = vnap = (Vernaux *)(vnd + 1);
2661 
2662 		has_specver = sdf && (sdf->sdf_flags & FLG_SDF_SPECVER);
2663 		if (has_specver) {
2664 			Sdv_desc	*sdv;
2665 			Listnode	*lnp2;
2666 
2667 			/*
2668 			 * If version needed definitions were specified in
2669 			 * a mapfile ($SPECVERS=*) then record those
2670 			 * definitions.
2671 			 */
2672 			for (LIST_TRAVERSE(&sdf->sdf_verneed, lnp2, sdv)) {
2673 				/*
2674 				 * If this $SPECVERS item corresponds
2675 				 * to a real version, then skip it here
2676 				 * in favor of the real one below.
2677 				 */
2678 				if (sdv->sdv_flags & FLG_SDV_MATCHED)
2679 					continue;
2680 
2681 				(void) st_setstring(dynstr, sdv->sdv_name,
2682 				    &stoff);
2683 				vnap->vna_name = stoff;
2684 				/* LINTED */
2685 				vnap->vna_hash = (Word)elf_hash(sdv->sdv_name);
2686 				vnap->vna_flags = 0;
2687 				vnap->vna_other = 0;
2688 				_vnap = vnap;
2689 				vnap++;
2690 				cnt++;
2691 				/* LINTED */
2692 				_vnap->vna_next = (Word)((uintptr_t)vnap -
2693 				    (uintptr_t)_vnap);
2694 			}
2695 		}
2696 
2697 		/*
2698 		 * Traverse the version index list recording
2699 		 * each version as a needed dependency.
2700 		 */
2701 		for (_cnt = 0; _cnt <= ifl->ifl_vercnt; _cnt++) {
2702 			Ver_index	*vip = &ifl->ifl_verndx[_cnt];
2703 
2704 			if (vip->vi_flags & FLG_VER_REFER) {
2705 				(void) st_setstring(dynstr, vip->vi_name,
2706 				    &stoff);
2707 				vnap->vna_name = stoff;
2708 
2709 				if (vip->vi_desc) {
2710 					vnap->vna_hash = vip->vi_desc->vd_hash;
2711 					vnap->vna_flags =
2712 					    vip->vi_desc->vd_flags;
2713 				} else {
2714 					vnap->vna_hash = 0;
2715 					vnap->vna_flags = 0;
2716 				}
2717 				vnap->vna_other = vip->vi_overndx;
2718 
2719 				/*
2720 				 * If version A inherits version B, then
2721 				 * B is implicit in A. It suffices for ld.so.1
2722 				 * to verify A at runtime and skip B. The
2723 				 * version normalization process sets the INFO
2724 				 * flag for the versions we want ld.so.1 to
2725 				 * skip. By default, we progagate these flags
2726 				 * to the output object as computed.
2727 				 *
2728 				 * The presence of $SPECVERS items alters
2729 				 * matters. If $SPECVERS are present in the
2730 				 * mapfile, then any version that corresponds
2731 				 * to the $SPECVERS must be validated, and
2732 				 * all others must be skipped. This is true
2733 				 * even if it causes ld.so.1 to incorrectly
2734 				 * validate the object ---- it is an override
2735 				 * mechanism.
2736 				 */
2737 				if ((!has_specver &&
2738 				    (vip->vi_flags & VER_FLG_INFO)) ||
2739 				    (has_specver &&
2740 				    !(vip->vi_flags & FLG_VER_SPECVER)))
2741 					vnap->vna_flags |= VER_FLG_INFO;
2742 
2743 				_vnap = vnap;
2744 				vnap++, cnt++;
2745 				_vnap->vna_next =
2746 				    /* LINTED */
2747 				    (Word)((uintptr_t)vnap - (uintptr_t)_vnap);
2748 			}
2749 		}
2750 
2751 		_vnap->vna_next = 0;
2752 
2753 		/*
2754 		 * Record the versions auxiliary array offset and
2755 		 * the associated dependency count.
2756 		 */
2757 		/* LINTED */
2758 		vnd->vn_aux = (Word)((uintptr_t)(vnd + 1) - (uintptr_t)vnd);
2759 		/* LINTED */
2760 		vnd->vn_cnt = (Half)cnt;
2761 
2762 		/*
2763 		 * Record the next versions offset and update the version
2764 		 * pointer.  Remember the previous version offset as the very
2765 		 * last structures next pointer should be null.
2766 		 */
2767 		_vnd = vnd;
2768 		vnd = (Verneed *)vnap, num++;
2769 		/* LINTED */
2770 		_vnd->vn_next = (Word)((uintptr_t)vnd - (uintptr_t)_vnd);
2771 	}
2772 	_vnd->vn_next = 0;
2773 
2774 	/*
2775 	 * Record association on string table section and use the
2776 	 * `info' field to indicate the number of entries in this
2777 	 * section.
2778 	 */
2779 	ofl->ofl_osverneed->os_shdr->sh_link =
2780 	    /* LINTED */
2781 	    (Word)elf_ndxscn(ofl->ofl_osdynstr->os_scn);
2782 	ofl->ofl_osverneed->os_shdr->sh_info = num;
2783 
2784 	return (1);
2785 }
2786 
2787 
2788 /*
2789  * Update syminfo section.
2790  */
2791 static uintptr_t
2792 update_osyminfo(Ofl_desc * ofl)
2793 {
2794 	Os_desc *	symosp, * infosp = ofl->ofl_ossyminfo;
2795 	Syminfo *	sip = infosp->os_outdata->d_buf;
2796 	Shdr *		shdr = infosp->os_shdr;
2797 	char		*strtab;
2798 	Listnode *	lnp;
2799 	Sym_desc *	sdp;
2800 	Aliste		idx;
2801 	Sfltr_desc *	sftp;
2802 
2803 	if (ofl->ofl_flags & FLG_OF_RELOBJ) {
2804 		symosp = ofl->ofl_ossymtab;
2805 		strtab = ofl->ofl_osstrtab->os_outdata->d_buf;
2806 	} else {
2807 		symosp = ofl->ofl_osdynsym;
2808 		strtab = ofl->ofl_osdynstr->os_outdata->d_buf;
2809 	}
2810 
2811 	/* LINTED */
2812 	infosp->os_shdr->sh_link = (Word)elf_ndxscn(symosp->os_scn);
2813 	if (ofl->ofl_osdynamic)
2814 		infosp->os_shdr->sh_info =
2815 		    /* LINTED */
2816 		    (Word)elf_ndxscn(ofl->ofl_osdynamic->os_scn);
2817 
2818 	/*
2819 	 * Update any references with the index into the dynamic table.
2820 	 */
2821 	for (LIST_TRAVERSE(&ofl->ofl_syminfsyms, lnp, sdp)) {
2822 		Ifl_desc *	ifl;
2823 		if (sdp->sd_aux && sdp->sd_aux->sa_bindto)
2824 			ifl = sdp->sd_aux->sa_bindto;
2825 		else
2826 			ifl = sdp->sd_file;
2827 		sip[sdp->sd_symndx].si_boundto = ifl->ifl_neededndx;
2828 	}
2829 
2830 	/*
2831 	 * Update any filtee references with the index into the dynamic table.
2832 	 */
2833 	for (ALIST_TRAVERSE(ofl->ofl_symfltrs, idx, sftp)) {
2834 		Dfltr_desc	*dftp;
2835 
2836 		dftp = alist_item(ofl->ofl_dtsfltrs, sftp->sft_idx);
2837 		sip[sftp->sft_sdp->sd_symndx].si_boundto = dftp->dft_ndx;
2838 	}
2839 
2840 	/*
2841 	 * Display debugging information about section.
2842 	 */
2843 	DBG_CALL(Dbg_syminfo_title(ofl->ofl_lml));
2844 	if (DBG_ENABLED) {
2845 		Word	_cnt, cnt = shdr->sh_size / shdr->sh_entsize;
2846 		Sym *	symtab = symosp->os_outdata->d_buf;
2847 		Dyn *	dyn;
2848 
2849 		if (ofl->ofl_osdynamic)
2850 			dyn = ofl->ofl_osdynamic->os_outdata->d_buf;
2851 		else
2852 			dyn = 0;
2853 
2854 		for (_cnt = 1; _cnt < cnt; _cnt++) {
2855 			if (sip[_cnt].si_flags || sip[_cnt].si_boundto)
2856 				/* LINTED */
2857 				DBG_CALL(Dbg_syminfo_entry(ofl->ofl_lml, _cnt,
2858 				    &sip[_cnt], &symtab[_cnt], strtab, dyn));
2859 		}
2860 	}
2861 	return (1);
2862 }
2863 
2864 /*
2865  * Build the output elf header.
2866  */
2867 static uintptr_t
2868 update_oehdr(Ofl_desc * ofl)
2869 {
2870 	Ehdr	*ehdr = ofl->ofl_nehdr;
2871 
2872 	/*
2873 	 * If an entry point symbol has already been established (refer
2874 	 * sym_validate()) simply update the elf header entry point with the
2875 	 * symbols value.  If no entry point is defined it will have been filled
2876 	 * with the start address of the first section within the text segment
2877 	 * (refer update_outfile()).
2878 	 */
2879 	if (ofl->ofl_entry)
2880 		ehdr->e_entry =
2881 		    ((Sym_desc *)(ofl->ofl_entry))->sd_sym->st_value;
2882 
2883 	/*
2884 	 * Note. it may be necessary to update the `e_flags' field in the
2885 	 * machine dependent section.
2886 	 */
2887 	ehdr->e_ident[EI_DATA] = ld_targ.t_m.m_data;
2888 	ehdr->e_machine = ofl->ofl_dehdr->e_machine;
2889 	ehdr->e_flags = ofl->ofl_dehdr->e_flags;
2890 	ehdr->e_version = ofl->ofl_dehdr->e_version;
2891 
2892 	if (ehdr->e_machine != ld_targ.t_m.m_mach) {
2893 		if (ehdr->e_machine != ld_targ.t_m.m_machplus)
2894 			return (S_ERROR);
2895 		if ((ehdr->e_flags & ld_targ.t_m.m_flagsplus) == 0)
2896 			return (S_ERROR);
2897 	}
2898 
2899 	if (ofl->ofl_flags & FLG_OF_SHAROBJ)
2900 		ehdr->e_type = ET_DYN;
2901 	else if (ofl->ofl_flags & FLG_OF_RELOBJ)
2902 		ehdr->e_type = ET_REL;
2903 	else
2904 		ehdr->e_type = ET_EXEC;
2905 
2906 	return (1);
2907 }
2908 
2909 /*
2910  * Perform move table expansion.
2911  */
2912 static uintptr_t
2913 expand_move(Ofl_desc *ofl, Sym_desc *sdp, Move *u1)
2914 {
2915 	Move		*mv;
2916 	Os_desc		*osp;
2917 	unsigned char	*taddr, *taddr0;
2918 	Sxword		offset;
2919 	int		i;
2920 	Addr		base1;
2921 	unsigned int	stride;
2922 
2923 	osp = ofl->ofl_issunwdata1->is_osdesc;
2924 	base1 = (Addr)(osp->os_shdr->sh_addr +
2925 	    ofl->ofl_issunwdata1->is_indata->d_off);
2926 	taddr0 = taddr = osp->os_outdata->d_buf;
2927 	mv = u1;
2928 
2929 	offset = sdp->sd_sym->st_value - base1;
2930 	taddr += offset;
2931 	taddr = taddr + mv->m_poffset;
2932 	for (i = 0; i < mv->m_repeat; i++) {
2933 		/* LINTED */
2934 		DBG_CALL(Dbg_move_expand(ofl->ofl_lml, mv,
2935 		    (Addr)(taddr - taddr0)));
2936 		stride = (unsigned int)mv->m_stride + 1;
2937 		/* LINTED */
2938 		switch (ELF_M_SIZE(mv->m_info)) {
2939 		case 1:
2940 			/* LINTED */
2941 			*taddr = (unsigned char)mv->m_value;
2942 			taddr += stride;
2943 			break;
2944 		case 2:
2945 			/* LINTED */
2946 			*((Half *)taddr) = (Half)mv->m_value;
2947 			taddr += 2*stride;
2948 			break;
2949 		case 4:
2950 			/* LINTED */
2951 			*((Word *)taddr) = (Word)mv->m_value;
2952 			taddr += 4*stride;
2953 			break;
2954 		case 8:
2955 			/* LINTED */
2956 			*((unsigned long long *)taddr) = mv->m_value;
2957 			taddr += 8*stride;
2958 			break;
2959 		default:
2960 			/*
2961 			 * Should never come here since this is already
2962 			 * checked at sunwmove_preprocess().
2963 			 */
2964 			return (S_ERROR);
2965 		}
2966 	}
2967 	return (1);
2968 }
2969 
2970 /*
2971  * Update Move sections.
2972  */
2973 static uintptr_t
2974 update_move(Ofl_desc *ofl)
2975 {
2976 	Word		ndx = 0;
2977 	Is_desc *	isp;
2978 	ofl_flag_t	flags = ofl->ofl_flags;
2979 	Move *		mv1, * mv2;
2980 	Listnode *	lnp1;
2981 	Psym_info *	psym;
2982 
2983 	/*
2984 	 * Determine the index of the symbol table that will be referenced by
2985 	 * the relocation entries.
2986 	 */
2987 	if (OFL_ALLOW_DYNSYM(ofl))
2988 		/* LINTED */
2989 		ndx = (Word) elf_ndxscn(ofl->ofl_osdynsym->os_scn);
2990 	else if (!(flags & FLG_OF_STRIP) || (flags & FLG_OF_RELOBJ))
2991 		/* LINTED */
2992 		ndx = (Word) elf_ndxscn(ofl->ofl_ossymtab->os_scn);
2993 
2994 	/*
2995 	 * update sh_link and mv pointer for updating move table.
2996 	 */
2997 	if (ofl->ofl_osmove) {
2998 		ofl->ofl_osmove->os_shdr->sh_link = ndx;
2999 		mv1 = (Move *) ofl->ofl_osmove->os_outdata->d_buf;
3000 	}
3001 
3002 	/*
3003 	 * Update symbol entry index
3004 	 */
3005 	for (LIST_TRAVERSE(&ofl->ofl_parsym, lnp1, psym)) {
3006 		Listnode *	lnp2;
3007 		Mv_itm *	mvp;
3008 		Sym_desc 	*sdp;
3009 
3010 		/*
3011 		 * Expand move table
3012 		 */
3013 		if (psym->psym_symd->sd_flags & FLG_SY_PAREXPN) {
3014 			const char	*s;
3015 
3016 			if (flags & FLG_OF_STATIC)
3017 				s = MSG_INTL(MSG_PSYM_EXPREASON1);
3018 			else if (ofl->ofl_flags1 & FLG_OF1_NOPARTI)
3019 				s = MSG_INTL(MSG_PSYM_EXPREASON2);
3020 			else
3021 				s = MSG_INTL(MSG_PSYM_EXPREASON3);
3022 			DBG_CALL(Dbg_move_parexpn(ofl->ofl_lml,
3023 			    psym->psym_symd->sd_name, s));
3024 			for (LIST_TRAVERSE(&(psym->psym_mvs), lnp2, mvp)) {
3025 				if ((mvp->mv_flag & FLG_MV_OUTSECT) == 0)
3026 					continue;
3027 				mv2 = mvp->mv_ientry;
3028 				sdp = psym->psym_symd;
3029 				DBG_CALL(Dbg_move_entry1(ofl->ofl_lml, 0,
3030 				    mv2, sdp));
3031 				(void) expand_move(ofl, sdp, mv2);
3032 			}
3033 			continue;
3034 		}
3035 
3036 		/*
3037 		 * Process move table
3038 		 */
3039 		DBG_CALL(Dbg_move_outmove(ofl->ofl_lml,
3040 		    psym->psym_symd->sd_name));
3041 		for (LIST_TRAVERSE(&(psym->psym_mvs), lnp2, mvp)) {
3042 			int	idx = 1;
3043 			Sym	*sym;
3044 
3045 			if ((mvp->mv_flag & FLG_MV_OUTSECT) == 0)
3046 				continue;
3047 
3048 			isp = mvp->mv_isp;
3049 			mv2 = mvp->mv_ientry;
3050 			sdp = isp->is_file->ifl_oldndx[ELF_M_SYM(mv2->m_info)];
3051 			sym = sdp->sd_sym;
3052 
3053 			DBG_CALL(Dbg_move_entry1(ofl->ofl_lml, 0, mv2, sdp));
3054 
3055 			*mv1 = *mv2;
3056 			if ((flags & FLG_OF_RELOBJ) == 0) {
3057 				if (ELF_ST_BIND(sym->st_info) == STB_LOCAL) {
3058 					Half	symbssndx = ofl->ofl_isbss->
3059 					    is_osdesc->os_scnsymndx;
3060 
3061 					mv1->m_info =
3062 					    /* LINTED */
3063 					    ELF_M_INFO(symbssndx, mv2->m_info);
3064 
3065 					if (ELF_ST_TYPE(sym->st_info) !=
3066 					    STT_SECTION) {
3067 						mv1->m_poffset = sym->st_value -
3068 						    ofl->ofl_isbss->is_osdesc->
3069 						    os_shdr->sh_addr +
3070 						    mv2->m_poffset;
3071 					}
3072 				} else {
3073 					mv1->m_info =
3074 					    /* LINTED */
3075 					    ELF_M_INFO(sdp->sd_symndx,
3076 					    mv2->m_info);
3077 				}
3078 			} else {
3079 				Boolean 	isredloc = FALSE;
3080 
3081 				if ((ELF_ST_BIND(sym->st_info) == STB_LOCAL) &&
3082 				    (ofl->ofl_flags & FLG_OF_REDLSYM))
3083 					isredloc = TRUE;
3084 
3085 				if (isredloc && !(sdp->sd_psyminfo)) {
3086 					Word	symndx = sdp->sd_isc->
3087 					    is_osdesc->os_scnsymndx;
3088 
3089 					mv1->m_info =
3090 					    /* LINTED */
3091 					    ELF_M_INFO(symndx, mv2->m_info);
3092 					mv1->m_poffset += sym->st_value;
3093 				} else {
3094 					if (isredloc)
3095 						DBG_CALL(Dbg_syms_reduce(ofl,
3096 						    DBG_SYM_REDUCE_RETAIN, sdp,
3097 						    idx,
3098 						    ofl->ofl_osmove->os_name));
3099 
3100 					mv1->m_info =
3101 					    /* LINTED */
3102 					    ELF_M_INFO(sdp->sd_symndx,
3103 					    mv2->m_info);
3104 				}
3105 			}
3106 			DBG_CALL(Dbg_move_entry1(ofl->ofl_lml, 1, mv1, sdp));
3107 			mv1++;
3108 			idx++;
3109 		}
3110 	}
3111 	return (1);
3112 }
3113 
3114 
3115 /*
3116  * Scan through the SHT_GROUP output sections.  Update their
3117  * sh_link/sh_info fields as well as the section contents.
3118  */
3119 static uintptr_t
3120 update_ogroup(Ofl_desc *ofl)
3121 {
3122 	Listnode	*lnp;
3123 	Os_desc		*osp;
3124 	uintptr_t	error = 0;
3125 
3126 	for (LIST_TRAVERSE(&ofl->ofl_osgroups, lnp, osp)) {
3127 		Is_desc		*isp;
3128 		Ifl_desc	*ifl;
3129 		Shdr		*shdr = osp->os_shdr;
3130 		Sym_desc	*sdp;
3131 		Xword		i, grpcnt;
3132 		Word		*gdata;
3133 
3134 		/*
3135 		 * Since input GROUP sections always create unique
3136 		 * output GROUP sections - we know there is only one
3137 		 * item on the list.
3138 		 */
3139 		isp = (Is_desc *)osp->os_isdescs.head->data;
3140 
3141 		ifl = isp->is_file;
3142 		sdp = ifl->ifl_oldndx[isp->is_shdr->sh_info];
3143 		shdr->sh_link = (Word)elf_ndxscn(ofl->ofl_ossymtab->os_scn);
3144 		shdr->sh_info = sdp->sd_symndx;
3145 
3146 		/*
3147 		 * Scan through the group data section and update
3148 		 * all of the links to new values.
3149 		 */
3150 		grpcnt = shdr->sh_size / shdr->sh_entsize;
3151 		gdata = (Word *)osp->os_outdata->d_buf;
3152 
3153 		for (i = 1; i < grpcnt; i++) {
3154 			Os_desc	*_osp;
3155 			Is_desc	*_isp = ifl->ifl_isdesc[gdata[i]];
3156 
3157 			/*
3158 			 * If the referenced section didn't make it to the
3159 			 * output file - just zero out the entry.
3160 			 */
3161 			if ((_osp = _isp->is_osdesc) == NULL)
3162 				gdata[i] = 0;
3163 			else
3164 				gdata[i] = (Word)elf_ndxscn(_osp->os_scn);
3165 		}
3166 	}
3167 	return (error);
3168 }
3169 
3170 static void
3171 update_ostrtab(Os_desc *osp, Str_tbl *stp, uint_t extra)
3172 {
3173 	Elf_Data	*data;
3174 
3175 	if (osp == 0)
3176 		return;
3177 
3178 	data = osp->os_outdata;
3179 	assert(data->d_size == (st_getstrtab_sz(stp) + extra));
3180 	(void) st_setstrbuf(stp, data->d_buf, data->d_size - extra);
3181 	/* If leaving an extra hole at the end, zero it */
3182 	if (extra > 0)
3183 		(void) memset((char *)data->d_buf + data->d_size - extra,
3184 		    0x0, extra);
3185 }
3186 
3187 /*
3188  * Translate the shdr->sh_{link, info} from its input section value to that
3189  * of the corresponding shdr->sh_{link, info} output section value.
3190  */
3191 static Word
3192 translate_link(Ofl_desc *ofl, Os_desc *osp, Word link, const char *msg)
3193 {
3194 	Is_desc *	isp;
3195 	Ifl_desc *	ifl;
3196 
3197 	/*
3198 	 * Don't translate the special section numbers.
3199 	 */
3200 	if (link >= SHN_LORESERVE)
3201 		return (link);
3202 
3203 	/*
3204 	 * Does this output section translate back to an input file.  If not
3205 	 * then there is no translation to do.  In this case we will assume that
3206 	 * if sh_link has a value, it's the right value.
3207 	 */
3208 	isp = (Is_desc *)osp->os_isdescs.head->data;
3209 	if ((ifl = isp->is_file) == NULL)
3210 		return (link);
3211 
3212 	/*
3213 	 * Sanity check to make sure that the sh_{link, info} value
3214 	 * is within range for the input file.
3215 	 */
3216 	if (link >= ifl->ifl_shnum) {
3217 		eprintf(ofl->ofl_lml, ERR_WARNING, msg, ifl->ifl_name,
3218 		    isp->is_name, EC_XWORD(link));
3219 		return (link);
3220 	}
3221 
3222 	/*
3223 	 * Follow the link to the input section.
3224 	 */
3225 	if ((isp = ifl->ifl_isdesc[link]) == 0)
3226 		return (0);
3227 	if ((osp = isp->is_osdesc) == 0)
3228 		return (0);
3229 
3230 	/* LINTED */
3231 	return ((Word)elf_ndxscn(osp->os_scn));
3232 }
3233 
3234 /*
3235  * Having created all of the necessary sections, segments, and associated
3236  * headers, fill in the program headers and update any other data in the
3237  * output image.  Some general rules:
3238  *
3239  *  o	If an interpreter is required always generate a PT_PHDR entry as
3240  *	well.  It is this entry that triggers the kernel into passing the
3241  *	interpreter an aux vector instead of just a file descriptor.
3242  *
3243  *  o	When generating an image that will be interpreted (ie. a dynamic
3244  *	executable, a shared object, or a static executable that has been
3245  *	provided with an interpreter - weird, but possible), make the initial
3246  *	loadable segment include both the ehdr and phdr[].  Both of these
3247  *	tables are used by the interpreter therefore it seems more intuitive
3248  *	to explicitly defined them as part of the mapped image rather than
3249  *	relying on page rounding by the interpreter to allow their access.
3250  *
3251  *  o	When generating a static image that does not require an interpreter
3252  *	have the first loadable segment indicate the address of the first
3253  *	.section as the start address (things like /kernel/unix and ufsboot
3254  *	expect this behavior).
3255  */
3256 uintptr_t
3257 ld_update_outfile(Ofl_desc *ofl)
3258 {
3259 	Addr		size, etext, vaddr = ofl->ofl_segorigin;
3260 	Listnode	*lnp1, *lnp2;
3261 	Sg_desc		*sgp, *dtracesgp = 0, *capsgp = 0;
3262 	Os_desc		*osp;
3263 	int		phdrndx = 0, segndx = -1, secndx;
3264 	int		dtracepndx, dtracesndx, cappndx, capsndx;
3265 	Ehdr		*ehdr = ofl->ofl_nehdr;
3266 	Shdr		*hshdr;
3267 	Phdr		*_phdr = 0;
3268 	Word		phdrsz = (ehdr->e_phnum * ehdr->e_phentsize), shscnndx;
3269 	ofl_flag_t	flags = ofl->ofl_flags;
3270 	Word		ehdrsz = ehdr->e_ehsize;
3271 	Boolean		nobits;
3272 	Off		offset;
3273 	Aliste		idx;
3274 
3275 	/*
3276 	 * Loop through the segment descriptors and pick out what we need.
3277 	 */
3278 	DBG_CALL(Dbg_seg_title(ofl->ofl_lml));
3279 	for (LIST_TRAVERSE(&ofl->ofl_segs, lnp1, sgp)) {
3280 		Phdr	*phdr = &(sgp->sg_phdr);
3281 		Xword 	p_align;
3282 
3283 		segndx++;
3284 
3285 		/*
3286 		 * If an interpreter is required generate a PT_INTERP and
3287 		 * PT_PHDR program header entry.  The PT_PHDR entry describes
3288 		 * the program header table itself.  This information will be
3289 		 * passed via the aux vector to the interpreter (ld.so.1).
3290 		 * The program header array is actually part of the first
3291 		 * loadable segment (and the PT_PHDR entry is the first entry),
3292 		 * therefore its virtual address isn't known until the first
3293 		 * loadable segment is processed.
3294 		 */
3295 		if (phdr->p_type == PT_PHDR) {
3296 			if (ofl->ofl_osinterp) {
3297 				phdr->p_offset = ehdr->e_phoff;
3298 				phdr->p_filesz = phdr->p_memsz = phdrsz;
3299 
3300 				DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3301 				ofl->ofl_phdr[phdrndx++] = *phdr;
3302 			}
3303 			continue;
3304 		}
3305 		if (phdr->p_type == PT_INTERP) {
3306 			if (ofl->ofl_osinterp) {
3307 				Shdr	*shdr = ofl->ofl_osinterp->os_shdr;
3308 
3309 				phdr->p_vaddr = phdr->p_memsz = 0;
3310 				phdr->p_offset = shdr->sh_offset;
3311 				phdr->p_filesz = shdr->sh_size;
3312 
3313 				DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3314 				ofl->ofl_phdr[phdrndx++] = *phdr;
3315 			}
3316 			continue;
3317 		}
3318 
3319 		/*
3320 		 * If we are creating a PT_SUNWDTRACE segment, remember where
3321 		 * the program header is.  The header values are assigned after
3322 		 * update_osym() has completed and the symbol table addresses
3323 		 * have been udpated.
3324 		 */
3325 		if (phdr->p_type == PT_SUNWDTRACE) {
3326 			if ((ofl->ofl_dtracesym) &&
3327 			    ((flags & FLG_OF_RELOBJ) == 0)) {
3328 				dtracesgp = sgp;
3329 				dtracesndx = segndx;
3330 				dtracepndx = phdrndx++;
3331 			}
3332 			continue;
3333 		}
3334 
3335 		/*
3336 		 * If a hardware/software capabilities section is required,
3337 		 * generate the PT_SUNWCAP header.  Note, as this comes before
3338 		 * the first loadable segment, we don't yet know its real
3339 		 * virtual address.  This is updated later.
3340 		 */
3341 		if (phdr->p_type == PT_SUNWCAP) {
3342 			if (ofl->ofl_oscap) {
3343 				capsgp = sgp;
3344 				capsndx = segndx;
3345 				cappndx = phdrndx++;
3346 			}
3347 			continue;
3348 		}
3349 
3350 		/*
3351 		 * As the dynamic program header occurs after the loadable
3352 		 * headers in the segment descriptor table, all the address
3353 		 * information for the .dynamic output section will have been
3354 		 * figured out by now.
3355 		 */
3356 		if (phdr->p_type == PT_DYNAMIC) {
3357 			if (OFL_ALLOW_DYNSYM(ofl)) {
3358 				Shdr	*shdr = ofl->ofl_osdynamic->os_shdr;
3359 
3360 				phdr->p_vaddr = shdr->sh_addr;
3361 				phdr->p_offset = shdr->sh_offset;
3362 				phdr->p_filesz = shdr->sh_size;
3363 				phdr->p_flags = ld_targ.t_m.m_dataseg_perm;
3364 
3365 				DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3366 				ofl->ofl_phdr[phdrndx++] = *phdr;
3367 			}
3368 			continue;
3369 		}
3370 
3371 		/*
3372 		 * As the AMD unwind program header occurs after the loadable
3373 		 * headers in the segment descriptor table, all the address
3374 		 * information for the .eh_frame output section will have been
3375 		 * figured out by now.
3376 		 */
3377 #if	defined(_ELF64)
3378 		if ((ld_targ.t_m.m_mach == EM_AMD64) &&
3379 		    (phdr->p_type == PT_SUNW_UNWIND)) {
3380 			Shdr	    *shdr;
3381 
3382 			if (ofl->ofl_unwindhdr == 0)
3383 				continue;
3384 
3385 			shdr = ofl->ofl_unwindhdr->os_shdr;
3386 
3387 			phdr->p_flags = PF_R;
3388 			phdr->p_vaddr = shdr->sh_addr;
3389 			phdr->p_memsz = shdr->sh_size;
3390 			phdr->p_filesz = shdr->sh_size;
3391 			phdr->p_offset = shdr->sh_offset;
3392 			phdr->p_align = shdr->sh_addralign;
3393 			phdr->p_paddr = 0;
3394 			ofl->ofl_phdr[phdrndx++] = *phdr;
3395 			continue;
3396 		}
3397 #endif
3398 		/*
3399 		 * As the TLS program header occurs after the loadable
3400 		 * headers in the segment descriptor table, all the address
3401 		 * information for the .tls output section will have been
3402 		 * figured out by now.
3403 		 */
3404 		if (phdr->p_type == PT_TLS) {
3405 			Os_desc	*tlsosp;
3406 			Shdr	*firstshdr = 0, *lastfileshdr = 0, *lastshdr;
3407 
3408 			if (ofl->ofl_ostlsseg.head == NULL)
3409 				continue;
3410 
3411 			/*
3412 			 * Scan through the sections that have contributed TLS.
3413 			 * Remember the first and last so as to determine the
3414 			 * TLS memory size requirement.  Remember the last
3415 			 * non-nobits section to determine the TLS data
3416 			 * contribution, which determines the TLS file size.
3417 			 */
3418 			for (LIST_TRAVERSE(&ofl->ofl_ostlsseg, lnp2, tlsosp)) {
3419 				Shdr	*tlsshdr = tlsosp->os_shdr;
3420 
3421 				if (firstshdr == 0)
3422 					firstshdr = tlsshdr;
3423 				if (tlsshdr->sh_type != SHT_NOBITS)
3424 					lastfileshdr = tlsshdr;
3425 				lastshdr = tlsshdr;
3426 			}
3427 
3428 			phdr->p_flags = PF_R | PF_W;
3429 			phdr->p_vaddr = firstshdr->sh_addr;
3430 			phdr->p_offset = firstshdr->sh_offset;
3431 			phdr->p_align = firstshdr->sh_addralign;
3432 
3433 			if (lastfileshdr)
3434 				phdr->p_filesz = lastfileshdr->sh_offset +
3435 				    lastfileshdr->sh_size - phdr->p_offset;
3436 			else
3437 				phdr->p_filesz = 0;
3438 
3439 			phdr->p_memsz = lastshdr->sh_offset +
3440 			    lastshdr->sh_size - phdr->p_offset;
3441 
3442 			DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3443 			ofl->ofl_phdr[phdrndx] = *phdr;
3444 			ofl->ofl_tlsphdr = &ofl->ofl_phdr[phdrndx++];
3445 			continue;
3446 		}
3447 
3448 		/*
3449 		 * If this is an empty segment declaration, it will occur after
3450 		 * all other loadable segments.  As empty segments can be
3451 		 * defind with fixed addresses, make sure that no loadable
3452 		 * segments overlap.  This might occur as the object evolves
3453 		 * and the loadable segments grow, thus encroaching upon an
3454 		 * existing segment reservation.
3455 		 *
3456 		 * Segments are only created for dynamic objects, thus this
3457 		 * checking can be skipped when building a relocatable object.
3458 		 */
3459 		if (!(flags & FLG_OF_RELOBJ) &&
3460 		    (sgp->sg_flags & FLG_SG_EMPTY)) {
3461 			int	i;
3462 			Addr	v_e;
3463 
3464 			vaddr = phdr->p_vaddr;
3465 			phdr->p_memsz = sgp->sg_length;
3466 			DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3467 			ofl->ofl_phdr[phdrndx++] = *phdr;
3468 
3469 			if (phdr->p_type != PT_LOAD)
3470 				continue;
3471 
3472 			v_e = vaddr + phdr->p_memsz;
3473 
3474 			/*
3475 			 * Check overlaps
3476 			 */
3477 			for (i = 0; i < phdrndx - 1; i++) {
3478 				Addr 	p_s = (ofl->ofl_phdr[i]).p_vaddr;
3479 				Addr 	p_e;
3480 
3481 				if ((ofl->ofl_phdr[i]).p_type != PT_LOAD)
3482 					continue;
3483 
3484 				p_e = p_s + (ofl->ofl_phdr[i]).p_memsz;
3485 				if (((p_s <= vaddr) && (p_e > vaddr)) ||
3486 				    ((vaddr <= p_s) && (v_e > p_s)))
3487 					eprintf(ofl->ofl_lml, ERR_WARNING,
3488 					    MSG_INTL(MSG_UPD_SEGOVERLAP),
3489 					    ofl->ofl_name, EC_ADDR(p_e),
3490 					    sgp->sg_name, EC_ADDR(vaddr));
3491 			}
3492 			continue;
3493 		}
3494 
3495 		/*
3496 		 * Having processed any of the special program headers any
3497 		 * remaining headers will be built to express individual
3498 		 * segments.  Segments are only built if they have output
3499 		 * section descriptors associated with them (ie. some form of
3500 		 * input section has been matched to this segment).
3501 		 */
3502 		if (sgp->sg_osdescs == NULL)
3503 			continue;
3504 
3505 		/*
3506 		 * Determine the segments offset and size from the section
3507 		 * information provided from elf_update().
3508 		 * Allow for multiple NOBITS sections.
3509 		 */
3510 		osp = sgp->sg_osdescs->apl_data[0];
3511 		hshdr = osp->os_shdr;
3512 
3513 		phdr->p_filesz = 0;
3514 		phdr->p_memsz = 0;
3515 		phdr->p_offset = offset = hshdr->sh_offset;
3516 
3517 		nobits = ((hshdr->sh_type == SHT_NOBITS) &&
3518 		    ((sgp->sg_flags & FLG_SG_PHREQ) == 0));
3519 
3520 		for (APLIST_TRAVERSE(sgp->sg_osdescs, idx, osp)) {
3521 			Shdr	*shdr = osp->os_shdr;
3522 
3523 			p_align = 0;
3524 			if (shdr->sh_addralign > p_align)
3525 				p_align = shdr->sh_addralign;
3526 
3527 			offset = (Off)S_ROUND(offset, shdr->sh_addralign);
3528 			offset += shdr->sh_size;
3529 
3530 			if (shdr->sh_type != SHT_NOBITS) {
3531 				if (nobits) {
3532 					eprintf(ofl->ofl_lml, ERR_FATAL,
3533 					    MSG_INTL(MSG_UPD_NOBITS));
3534 					return (S_ERROR);
3535 				}
3536 				phdr->p_filesz = offset - phdr->p_offset;
3537 			} else if ((sgp->sg_flags & FLG_SG_PHREQ) == 0)
3538 				nobits = TRUE;
3539 		}
3540 		phdr->p_memsz = offset - hshdr->sh_offset;
3541 
3542 		/*
3543 		 * If this is PT_SUNWBSS, set alignment
3544 		 */
3545 		if (phdr->p_type == PT_SUNWBSS)
3546 			phdr->p_align = p_align;
3547 
3548 		/*
3549 		 * If this is the first loadable segment of a dynamic object,
3550 		 * or an interpreter has been specified (a static object built
3551 		 * with an interpreter will still be given a PT_HDR entry), then
3552 		 * compensate for the elf header and program header array.  Both
3553 		 * of these are actually part of the loadable segment as they
3554 		 * may be inspected by the interpreter.  Adjust the segments
3555 		 * size and offset accordingly.
3556 		 */
3557 		if ((_phdr == 0) && (phdr->p_type == PT_LOAD) &&
3558 		    ((ofl->ofl_osinterp) || (flags & FLG_OF_DYNAMIC)) &&
3559 		    (!(ofl->ofl_dtflags_1 & DF_1_NOHDR))) {
3560 			size = (Addr)S_ROUND((phdrsz + ehdrsz),
3561 			    hshdr->sh_addralign);
3562 			phdr->p_offset -= size;
3563 			phdr->p_filesz += size;
3564 			phdr->p_memsz += size;
3565 		}
3566 
3567 		/*
3568 		 * If a segment size symbol is required (specified via a
3569 		 * mapfile) update its value.
3570 		 */
3571 		if (sgp->sg_sizesym != NULL)
3572 			sgp->sg_sizesym->sd_sym->st_value = phdr->p_memsz;
3573 
3574 		/*
3575 		 * If no file content has been assigned to this segment (it
3576 		 * only contains no-bits sections), then reset the offset for
3577 		 * consistency.
3578 		 */
3579 		if (phdr->p_filesz == 0)
3580 			phdr->p_offset = 0;
3581 
3582 		/*
3583 		 * If a virtual address has been specified for this segment
3584 		 * (presumably from a map file) use it and make sure the
3585 		 * previous segment does not run into this segment.
3586 		 */
3587 		if ((phdr->p_type == PT_LOAD) ||
3588 		    (phdr->p_type == PT_SUNWBSS)) {
3589 			if ((sgp->sg_flags & FLG_SG_VADDR)) {
3590 				if (_phdr && (vaddr > phdr->p_vaddr) &&
3591 				    (phdr->p_type == PT_LOAD))
3592 					eprintf(ofl->ofl_lml, ERR_WARNING,
3593 					    MSG_INTL(MSG_UPD_SEGOVERLAP),
3594 					    ofl->ofl_name, EC_ADDR(vaddr),
3595 					    sgp->sg_name,
3596 					    EC_ADDR(phdr->p_vaddr));
3597 				vaddr = phdr->p_vaddr;
3598 				phdr->p_align = 0;
3599 			} else {
3600 				vaddr = phdr->p_vaddr =
3601 				    (Addr)S_ROUND(vaddr, phdr->p_align);
3602 			}
3603 		}
3604 
3605 		/*
3606 		 * Adjust the address offset and p_align if needed.
3607 		 */
3608 		if (((sgp->sg_flags & FLG_SG_VADDR) == 0) &&
3609 		    ((ofl->ofl_dtflags_1 & DF_1_NOHDR) == 0)) {
3610 			if (phdr->p_align != 0)
3611 				vaddr += phdr->p_offset % phdr->p_align;
3612 			else
3613 				vaddr += phdr->p_offset;
3614 			phdr->p_vaddr = vaddr;
3615 		}
3616 
3617 		/*
3618 		 * If an interpreter is required set the virtual address of the
3619 		 * PT_PHDR program header now that we know the virtual address
3620 		 * of the loadable segment that contains it.  Update the
3621 		 * PT_SUNWCAP header similarly.
3622 		 */
3623 		if ((_phdr == 0) && (phdr->p_type == PT_LOAD)) {
3624 			_phdr = phdr;
3625 
3626 			if ((ofl->ofl_dtflags_1 & DF_1_NOHDR) == 0) {
3627 				if (ofl->ofl_osinterp)
3628 					ofl->ofl_phdr[0].p_vaddr =
3629 					    vaddr + ehdrsz;
3630 
3631 				/*
3632 				 * Finally, if we're creating a dynamic object
3633 				 * (or a static object in which an interpreter
3634 				 * is specified) update the vaddr to reflect
3635 				 * the address of the first section within this
3636 				 * segment.
3637 				 */
3638 				if ((ofl->ofl_osinterp) ||
3639 				    (flags & FLG_OF_DYNAMIC))
3640 					vaddr += size;
3641 			} else {
3642 				/*
3643 				 * If the DF_1_NOHDR flag was set, and an
3644 				 * interpreter is being generated, the PT_PHDR
3645 				 * will not be part of any loadable segment.
3646 				 */
3647 				if (ofl->ofl_osinterp) {
3648 					ofl->ofl_phdr[0].p_vaddr = 0;
3649 					ofl->ofl_phdr[0].p_memsz = 0;
3650 					ofl->ofl_phdr[0].p_flags = 0;
3651 				}
3652 			}
3653 		}
3654 
3655 		/*
3656 		 * Ensure the ELF entry point defaults to zero.  Typically, this
3657 		 * value is overridden in update_oehdr() to one of the standard
3658 		 * entry points.  Historically, this default was set to the
3659 		 * address of first executable section, but this has since been
3660 		 * found to be more confusing than it is helpful.
3661 		 */
3662 		ehdr->e_entry = 0;
3663 
3664 		DBG_CALL(Dbg_seg_entry(ofl, segndx, sgp));
3665 
3666 		/*
3667 		 * Traverse the output section descriptors for this segment so
3668 		 * that we can update the section headers addresses.  We've
3669 		 * calculated the virtual address of the initial section within
3670 		 * this segment, so each successive section can be calculated
3671 		 * based on their offsets from each other.
3672 		 */
3673 		secndx = 0;
3674 		hshdr = 0;
3675 		for (APLIST_TRAVERSE(sgp->sg_osdescs, idx, osp)) {
3676 			Shdr	*shdr = osp->os_shdr;
3677 
3678 			if (shdr->sh_link)
3679 				shdr->sh_link = translate_link(ofl, osp,
3680 				    shdr->sh_link, MSG_INTL(MSG_FIL_INVSHLINK));
3681 
3682 			if (shdr->sh_info && (shdr->sh_flags & SHF_INFO_LINK))
3683 				shdr->sh_info = translate_link(ofl, osp,
3684 				    shdr->sh_info, MSG_INTL(MSG_FIL_INVSHINFO));
3685 
3686 			if (!(flags & FLG_OF_RELOBJ) &&
3687 			    (phdr->p_type == PT_LOAD) ||
3688 			    (phdr->p_type == PT_SUNWBSS)) {
3689 				if (hshdr)
3690 					vaddr += (shdr->sh_offset -
3691 					    hshdr->sh_offset);
3692 
3693 				shdr->sh_addr = vaddr;
3694 				hshdr = shdr;
3695 			}
3696 
3697 			DBG_CALL(Dbg_seg_os(ofl, osp, secndx));
3698 			secndx++;
3699 		}
3700 
3701 		/*
3702 		 * Establish the virtual address of the end of the last section
3703 		 * in this segment so that the next segments offset can be
3704 		 * calculated from this.
3705 		 */
3706 		if (hshdr)
3707 			vaddr += hshdr->sh_size;
3708 
3709 		/*
3710 		 * Output sections for this segment complete.  Adjust the
3711 		 * virtual offset for the last sections size, and make sure we
3712 		 * haven't exceeded any maximum segment length specification.
3713 		 */
3714 		if ((sgp->sg_length != 0) && (sgp->sg_length < phdr->p_memsz)) {
3715 			eprintf(ofl->ofl_lml, ERR_FATAL,
3716 			    MSG_INTL(MSG_UPD_LARGSIZE), ofl->ofl_name,
3717 			    sgp->sg_name, EC_XWORD(phdr->p_memsz),
3718 			    EC_XWORD(sgp->sg_length));
3719 			return (S_ERROR);
3720 		}
3721 
3722 		if (phdr->p_type == PT_NOTE) {
3723 			phdr->p_vaddr = 0;
3724 			phdr->p_paddr = 0;
3725 			phdr->p_align = 0;
3726 			phdr->p_memsz = 0;
3727 		}
3728 
3729 		if ((phdr->p_type != PT_NULL) && !(flags & FLG_OF_RELOBJ))
3730 			ofl->ofl_phdr[phdrndx++] = *phdr;
3731 	}
3732 
3733 	/*
3734 	 * Update any new output sections.  When building the initial output
3735 	 * image, a number of sections were created but left uninitialized (eg.
3736 	 * .dynsym, .dynstr, .symtab, .symtab, etc.).  Here we update these
3737 	 * sections with the appropriate data.  Other sections may still be
3738 	 * modified via reloc_process().
3739 	 *
3740 	 * Copy the interpreter name into the .interp section.
3741 	 */
3742 	if (ofl->ofl_interp)
3743 		(void) strcpy((char *)ofl->ofl_osinterp->os_outdata->d_buf,
3744 		    ofl->ofl_interp);
3745 
3746 	/*
3747 	 * Update the .shstrtab, .strtab and .dynstr sections.
3748 	 */
3749 	update_ostrtab(ofl->ofl_osshstrtab, ofl->ofl_shdrsttab, 0);
3750 	update_ostrtab(ofl->ofl_osstrtab, ofl->ofl_strtab, 0);
3751 	update_ostrtab(ofl->ofl_osdynstr, ofl->ofl_dynstrtab, DYNSTR_EXTRA_PAD);
3752 
3753 	/*
3754 	 * Build any output symbol tables, the symbols information is copied
3755 	 * and updated into the new output image.
3756 	 */
3757 	if ((etext = update_osym(ofl)) == (Addr)S_ERROR)
3758 		return (S_ERROR);
3759 
3760 	/*
3761 	 * If we have a PT_SUNWDTRACE phdr, update it now with the address of
3762 	 * the symbol.  It's only now been updated via update_sym().
3763 	 */
3764 	if (dtracesgp && ofl->ofl_dtracesym) {
3765 		Phdr		*aphdr, *phdr = &(dtracesgp->sg_phdr);
3766 		Sym_desc	*sdp = ofl->ofl_dtracesym;
3767 
3768 		phdr->p_vaddr = sdp->sd_sym->st_value;
3769 		phdr->p_memsz = sdp->sd_sym->st_size;
3770 
3771 		/*
3772 		 * Take permisions of the segment the symbol is associated with.
3773 		 */
3774 		aphdr = &sdp->sd_isc->is_osdesc->os_sgdesc->sg_phdr;
3775 		assert(aphdr);
3776 		phdr->p_flags = aphdr->p_flags;
3777 
3778 		DBG_CALL(Dbg_seg_entry(ofl, dtracesndx, dtracesgp));
3779 		ofl->ofl_phdr[dtracepndx] = *phdr;
3780 	}
3781 
3782 	/*
3783 	 * If we have a PT_SUNWCAP phdr, update it now from the associated
3784 	 * section information.
3785 	 */
3786 	if (capsgp && ofl->ofl_oscap) {
3787 		Phdr	*phdr = &(capsgp->sg_phdr);
3788 		Shdr	*shdr = ofl->ofl_oscap->os_shdr;
3789 
3790 		phdr->p_vaddr = shdr->sh_addr;
3791 		phdr->p_offset = shdr->sh_offset;
3792 		phdr->p_filesz = shdr->sh_size;
3793 		phdr->p_flags = PF_R;
3794 
3795 		DBG_CALL(Dbg_seg_entry(ofl, capsndx, capsgp));
3796 		ofl->ofl_phdr[cappndx] = *phdr;
3797 	}
3798 
3799 	/*
3800 	 * Update the GROUP sections.
3801 	 */
3802 	if (update_ogroup(ofl) == S_ERROR)
3803 		return (S_ERROR);
3804 
3805 	/*
3806 	 * Update Move Table.
3807 	 */
3808 	if (ofl->ofl_osmove || ofl->ofl_issunwdata1) {
3809 		if (update_move(ofl) == S_ERROR)
3810 			return (S_ERROR);
3811 	}
3812 
3813 	/*
3814 	 * Build any output headers, version information, dynamic structure and
3815 	 * syminfo structure.
3816 	 */
3817 	if (update_oehdr(ofl) == S_ERROR)
3818 		return (S_ERROR);
3819 	if (!(flags & FLG_OF_NOVERSEC)) {
3820 		if ((flags & FLG_OF_VERDEF) &&
3821 		    (update_overdef(ofl) == S_ERROR))
3822 			return (S_ERROR);
3823 		if ((flags & FLG_OF_VERNEED) &&
3824 		    (update_overneed(ofl) == S_ERROR))
3825 			return (S_ERROR);
3826 		if ((flags & (FLG_OF_VERNEED | FLG_OF_VERDEF)) &&
3827 		    (update_oversym(ofl) == S_ERROR))
3828 			return (S_ERROR);
3829 	}
3830 	if (flags & FLG_OF_DYNAMIC) {
3831 		if (update_odynamic(ofl) == S_ERROR)
3832 			return (S_ERROR);
3833 		if (ofl->ofl_ossyminfo)
3834 			if (update_osyminfo(ofl) == S_ERROR)
3835 				return (S_ERROR);
3836 	}
3837 
3838 	/*
3839 	 * Emit Strtab diagnostics.
3840 	 */
3841 	DBG_CALL(Dbg_sec_strtab(ofl->ofl_lml, ofl->ofl_osshstrtab,
3842 	    ofl->ofl_shdrsttab));
3843 	DBG_CALL(Dbg_sec_strtab(ofl->ofl_lml, ofl->ofl_osstrtab,
3844 	    ofl->ofl_strtab));
3845 	DBG_CALL(Dbg_sec_strtab(ofl->ofl_lml, ofl->ofl_osdynstr,
3846 	    ofl->ofl_dynstrtab));
3847 
3848 	/*
3849 	 * Initialize the section headers string table index within the elf
3850 	 * header.
3851 	 */
3852 	/* LINTED */
3853 	if ((shscnndx = elf_ndxscn(ofl->ofl_osshstrtab->os_scn)) <
3854 	    SHN_LORESERVE) {
3855 		ofl->ofl_nehdr->e_shstrndx =
3856 		    /* LINTED */
3857 		    (Half)shscnndx;
3858 	} else {
3859 		/*
3860 		 * If the STRTAB section index doesn't fit into
3861 		 * e_shstrndx, then we store it in 'shdr[0].st_link'.
3862 		 */
3863 		Elf_Scn	*scn;
3864 		Shdr	*shdr0;
3865 
3866 		if ((scn = elf_getscn(ofl->ofl_elf, 0)) == NULL) {
3867 			eprintf(ofl->ofl_lml, ERR_ELF,
3868 			    MSG_INTL(MSG_ELF_GETSCN), ofl->ofl_name);
3869 			return (S_ERROR);
3870 		}
3871 		if ((shdr0 = elf_getshdr(scn)) == NULL) {
3872 			eprintf(ofl->ofl_lml, ERR_ELF,
3873 			    MSG_INTL(MSG_ELF_GETSHDR), ofl->ofl_name);
3874 			return (S_ERROR);
3875 		}
3876 		ofl->ofl_nehdr->e_shstrndx = SHN_XINDEX;
3877 		shdr0->sh_link = shscnndx;
3878 	}
3879 
3880 	return ((uintptr_t)etext);
3881 }
3882