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 2009 Sun Microsystems, Inc. All rights reserved. 27 * Use is subject to license terms. 28 */ 29 30 /* 31 * Symbol table resolution 32 */ 33 #define ELF_TARGET_AMD64 34 35 #include <stdio.h> 36 #include <debug.h> 37 #include "msg.h" 38 #include "_libld.h" 39 40 41 /* 42 * Categorize the symbol types that are applicable to the resolution process. 43 */ 44 typedef enum { 45 SYM_DEFINED, /* Defined symbol (SHN_ABS or shndx != 0) */ 46 SYM_UNDEFINED, /* Undefined symbol (SHN_UNDEF) */ 47 SYM_TENTATIVE, /* Tentative symbol (SHN_COMMON) */ 48 SYM_NUM /* the number of symbol types */ 49 } Symtype; 50 51 /* 52 * Do nothing. 53 */ 54 /* ARGSUSED0 */ 55 static void 56 sym_null(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 57 int ndx, Word nshndx, Word nsymflags) 58 { 59 } 60 61 static void 62 sym_visibility_diag(Error err, Sym_desc *sdp, Sym *osym, Sym *nsym, 63 Ifl_desc *ifl, Ofl_desc *ofl) 64 { 65 Conv_inv_buf_t inv_obuf, inv_nbuf; 66 67 eprintf(ofl->ofl_lml, err, MSG_INTL(MSG_SYM_CONFVIS), 68 demangle(sdp->sd_name)); 69 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_VISTYPES), 70 sdp->sd_file->ifl_name, conv_sym_other(osym->st_other, &inv_obuf), 71 ifl->ifl_name, conv_sym_other(nsym->st_other, &inv_nbuf)); 72 73 if (err == ERR_FATAL) 74 ofl->ofl_flags |= FLG_OF_FATAL; 75 else 76 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_DEFTAKEN), 77 ifl->ifl_name); 78 } 79 80 /* 81 * STV_VISIBILITY rules for STV_DEFAULT/INTERNAL/HIDDEN/PROTECTED say that the 82 * most restrictive visibility value should be taken. The precedence is: 83 * 84 * (most restrictive) INTERNAL -> HIDDEN -> PROTECTED -> DEFAULT (least) 85 * 86 * The STV_EXPORT and STV_SINGLETON visibilities are slightly different, in that 87 * the visibility must remain global and can not be reduced in any way. 88 * 89 * Resolution of different visibilities between two relocatable objects can 90 * take the following actions: 91 * 92 * i. if applicable, the most restrictive action is silently taken. 93 * ii. if a mapfile visibility definition competes with a more restrictive 94 * relocatable object definition, then a warning is generated, but the 95 * the more restrictive visibility is taken. 96 * iii. in the case of conflicts with an EXPORTED or SINGLETON symbol with 97 * any type of visibility between relocatable objects, the combination 98 * is deemed fatal. 99 * 100 * new visibility 101 * D I H P X S 102 * ------------------------------------------------------------ 103 * D | D I(mw) H(mw) P X S 104 * original I | I I I I X(mw/of) S(mw/of) 105 * visibility H | H I(mw) H H X(mw/of) S(mw/of) 106 * P | P I(mw) H(mw) P X(mw/of) S(mw/of) 107 * X | X I(mw/of) H(mw/of) P(mw/of) X S 108 * S | S I(mw/of) H(mw/of) P(mw/of) S S 109 * where: 110 * 111 * mw - mapfile warning: if the original symbol originates from a mapfile 112 * then warn the user that their scope definition is being overridden. 113 * of - object definitions are fatal: any combination of relocatable object 114 * visibilities that conflict with a SINGLETON and EXPORTED are fatal. 115 * 116 * Note, an eliminate symbol (STV_ELIMINATE) is treated as hidden (STV_HIDDEN) 117 * for processing through this state table. 118 */ 119 static Half 120 sym_visibility(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl) 121 { 122 Sym *osym = sdp->sd_sym; 123 uchar_t wovis, ovis; 124 uchar_t wnvis, nvis; 125 126 wovis = ovis = ELF_ST_VISIBILITY(osym->st_other); 127 wnvis = nvis = ELF_ST_VISIBILITY(nsym->st_other); 128 129 /* 130 * If the original visibilities are eliminate, assign them hidden for 131 * the state table processing. The original visibility, rather than 132 * the working visibility, will be returned to the caller. 133 */ 134 if (wovis == STV_ELIMINATE) 135 wovis = STV_HIDDEN; 136 if (wnvis == STV_ELIMINATE) 137 wnvis = STV_HIDDEN; 138 139 /* 140 * The most complex visibility resolution is between two relocatable 141 * objects. However, in the case of SINGLETONS we also want to catch 142 * any singleton definitions within shared objects. Relocatable objects 143 * that bind to these symbols inherit the singleton visibility as this 144 * efficiently triggers ld.so.1 into carrying out the appropriate 145 * runtime symbol search. Any other resolution between a relocatable 146 * object and a shared object will retain the relocatable objects 147 * visibility. 148 */ 149 if ((sdp->sd_ref == REF_REL_NEED) && 150 (ifl->ifl_ehdr->e_type == ET_DYN)) { 151 if ((sdp->sd_sym->st_shndx == SHN_UNDEF) && 152 (nsym->st_shndx != SHN_UNDEF) && (wnvis == STV_SINGLETON)) 153 return (STV_SINGLETON); 154 else 155 return (ovis); 156 } 157 if ((sdp->sd_ref != REF_REL_NEED) && 158 (ifl->ifl_ehdr->e_type == ET_REL)) { 159 if ((sdp->sd_sym->st_shndx != SHN_UNDEF) && 160 (nsym->st_shndx == SHN_UNDEF) && (wovis == STV_SINGLETON)) 161 return (STV_SINGLETON); 162 else 163 return (nvis); 164 } 165 166 /* 167 * If the visibilities are the same, we're done. If the working 168 * visibilities differ from the original, then one must have been 169 * STV_HIDDEN and the other STV_ELIMINATE. 170 */ 171 if (wovis == wnvis) { 172 if (ovis == nvis) 173 return (nvis); 174 else 175 return (STV_ELIMINATE); 176 } 177 178 /* 179 * An EXPORTED symbol or SINGLETON symbol can not be demoted, any 180 * conflicting visibility from another object is fatal. A conflicting 181 * visibility from a mapfile produces a warning, as the mapfile 182 * definition can be overridden. 183 */ 184 if ((wnvis == STV_EXPORTED) || (wnvis == STV_SINGLETON)) { 185 if ((wovis != STV_DEFAULT) && (wovis != STV_EXPORTED) && 186 (wovis != STV_SINGLETON)) { 187 if (sdp->sd_flags1 & FLG_SY1_MAPFILE) { 188 sym_visibility_diag(ERR_WARNING, sdp, osym, 189 nsym, ifl, ofl); 190 } else { 191 sym_visibility_diag(ERR_FATAL, sdp, osym, 192 nsym, ifl, ofl); 193 } 194 } 195 return (nvis); 196 } 197 if (wovis == STV_SINGLETON) { 198 if ((wnvis == STV_EXPORTED) || (wnvis == STV_DEFAULT)) 199 return (STV_SINGLETON); 200 if (sdp->sd_flags1 & FLG_SY1_MAPFILE) { 201 sym_visibility_diag(ERR_WARNING, sdp, osym, 202 nsym, ifl, ofl); 203 } else { 204 sym_visibility_diag(ERR_FATAL, sdp, osym, 205 nsym, ifl, ofl); 206 } 207 return (nvis); 208 } 209 if (wovis == STV_EXPORTED) { 210 if (wnvis == STV_SINGLETON) 211 return (STV_SINGLETON); 212 if (wnvis == STV_DEFAULT) 213 return (STV_EXPORTED); 214 if (sdp->sd_flags1 & FLG_SY1_MAPFILE) { 215 sym_visibility_diag(ERR_WARNING, sdp, osym, 216 nsym, ifl, ofl); 217 } else { 218 sym_visibility_diag(ERR_FATAL, sdp, osym, 219 nsym, ifl, ofl); 220 } 221 return (nvis); 222 } 223 224 /* 225 * Now that symbols with the same visibility, and all instances of 226 * SINGLETON's have been dealt with, we're left with visibilities that 227 * differ, but can be dealt with in the order of how restrictive the 228 * visibilities are. When a differing visibility originates from a 229 * mapfile definition, produces a warning, as the mapfile definition 230 * can be overridden by the relocatable object. 231 */ 232 if ((wnvis == STV_INTERNAL) || (wovis == STV_INTERNAL)) { 233 if ((wnvis == STV_INTERNAL) && 234 (sdp->sd_flags1 & FLG_SY1_MAPFILE)) { 235 sym_visibility_diag(ERR_WARNING, sdp, osym, nsym, 236 ifl, ofl); 237 } 238 return (STV_INTERNAL); 239 240 } else if ((wnvis == STV_HIDDEN) || (wovis == STV_HIDDEN)) { 241 if ((wnvis == STV_HIDDEN) && 242 (sdp->sd_flags1 & FLG_SY1_MAPFILE)) { 243 sym_visibility_diag(ERR_WARNING, sdp, osym, nsym, 244 ifl, ofl); 245 } 246 247 /* 248 * In the case of STV_ELIMINATE and STV_HIDDEN, the working 249 * visibility can differ from the original visibility, so make 250 * sure to return the original visibility. 251 */ 252 if ((ovis == STV_ELIMINATE) || (nvis == STV_ELIMINATE)) 253 return (STV_ELIMINATE); 254 else 255 return (STV_HIDDEN); 256 257 } else if ((wnvis == STV_PROTECTED) || (wovis == STV_PROTECTED)) 258 return (STV_PROTECTED); 259 260 return (STV_DEFAULT); 261 } 262 263 /* 264 * Check if two symbols types are compatible 265 */ 266 /*ARGSUSED4*/ 267 static void 268 sym_typecheck(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 269 int ndx, Word nshndx, Word nsymflags) 270 { 271 uchar_t otype = ELF_ST_TYPE(sdp->sd_sym->st_info); 272 uchar_t ntype = ELF_ST_TYPE(nsym->st_info); 273 Conv_inv_buf_t inv_buf1, inv_buf2; 274 275 /* 276 * Perform any machine specific type checking. 277 */ 278 if ((ld_targ.t_ms.ms_mach_sym_typecheck != NULL) && 279 (*ld_targ.t_ms.ms_mach_sym_typecheck)(sdp, nsym, ifl, ofl)) 280 return; 281 282 /* 283 * NOTYPE's can be combined with other types, only give an error if 284 * combining two differing types without NOTYPE. 285 */ 286 if ((otype == ntype) || (otype == STT_NOTYPE) || (ntype == STT_NOTYPE)) 287 return; 288 289 eprintf(ofl->ofl_lml, ERR_WARNING, MSG_INTL(MSG_SYM_DIFFTYPE), 290 demangle(sdp->sd_name)); 291 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_FILETYPES), 292 sdp->sd_file->ifl_name, 293 conv_sym_info_type(ofl->ofl_dehdr->e_machine, otype, 0, &inv_buf1), 294 ifl->ifl_name, 295 conv_sym_info_type(ofl->ofl_dehdr->e_machine, ntype, 0, &inv_buf2)); 296 } 297 298 /*ARGSUSED4*/ 299 static void 300 sym_mach_check(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 301 int ndx, Word nshndx, Word nsymflags) 302 { 303 /* 304 * Perform any machine specific type checking. 305 */ 306 if (ld_targ.t_ms.ms_mach_sym_typecheck != NULL) 307 (void) (*ld_targ.t_ms.ms_mach_sym_typecheck)(sdp, nsym, 308 ifl, ofl); 309 } 310 311 /* 312 * Promote the symbols reference. 313 */ 314 static void 315 /* ARGSUSED4 */ 316 sym_promote(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 317 int ndx, Word nshndx, Word nsymflags) 318 { 319 Word shndx = nsym->st_shndx; 320 321 sym_typecheck(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 322 323 /* 324 * If the old symbol is from a shared object and the new symbol is a 325 * reference from a relocatable object, promote the old symbols 326 * reference. 327 */ 328 if ((sdp->sd_ref == REF_DYN_SEEN) && 329 (ifl->ifl_ehdr->e_type == ET_REL)) { 330 sdp->sd_ref = REF_DYN_NEED; 331 332 /* 333 * If this is an undefined symbol it must be a relocatable 334 * object overriding a shared object. In this case also 335 * override the reference name so that any undefined symbol 336 * diagnostics will refer to the relocatable object name. 337 */ 338 if (shndx == SHN_UNDEF) 339 sdp->sd_aux->sa_rfile = ifl->ifl_name; 340 341 /* 342 * If this symbol is an undefined, or common, determine whether 343 * it is a global or weak reference (see build_osym(), where 344 * REF_DYN_NEED definitions are returned back to undefines). 345 */ 346 if (((shndx == SHN_UNDEF) || ((nsymflags & FLG_SY_SPECSEC) && 347 (shndx == SHN_COMMON))) && 348 (ELF_ST_BIND(nsym->st_info) == STB_GLOBAL)) 349 sdp->sd_flags |= FLG_SY_GLOBREF; 350 351 } else if ((shndx != SHN_UNDEF) && (ofl->ofl_dtflags_1 & DF_1_TRANS) && 352 (sdp->sd_aux->sa_bindto == 0) && (sdp->sd_ref == REF_REL_NEED) && 353 (ifl->ifl_ehdr->e_type == ET_DYN)) { 354 /* 355 * If building a translator then record the symbol 356 * we would 'bindto' with direct bindings. 357 */ 358 sdp->sd_aux->sa_bindto = ifl; 359 } 360 } 361 362 /* 363 * Override a symbol. 364 */ 365 static void 366 sym_override(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 367 int ndx, Word nshndx, Word nsymflags) 368 { 369 Sym *osym = sdp->sd_sym; 370 Word link; 371 372 /* 373 * In the case of a WEAK UNDEF symbol don't let a symbol from an 374 * unavailable object override the symbol definition. This is because 375 * this symbol *may* not be present in a future object and by promoting 376 * this symbol we are actually causing bindings (PLTS) to be formed 377 * to this symbol. Instead let the 'generic' weak binding take place. 378 */ 379 if ((ELF_ST_BIND(osym->st_info) == STB_WEAK) && 380 (sdp->sd_sym->st_shndx == SHN_UNDEF) && 381 ((ifl->ifl_flags & FLG_IF_NEEDED) == 0)) 382 return; 383 384 sym_typecheck(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 385 386 /* 387 * This symbol has already been compared to an SO definition, 388 * as per the runtime behavior, ignore extra definitions. 389 */ 390 if ((sdp->sd_flags & FLG_SY_SOFOUND) && 391 (ifl->ifl_ehdr->e_type == ET_DYN)) 392 return; 393 394 /* 395 * Mark the symbol as available and copy the new symbols contents. 396 */ 397 sdp->sd_flags &= ~FLG_SY_NOTAVAIL; 398 *osym = *nsym; 399 sdp->sd_shndx = nshndx; 400 sdp->sd_flags &= ~FLG_SY_SPECSEC; 401 sdp->sd_flags |= (nsymflags & (FLG_SY_SPECSEC | FLG_SY_TENTSYM)); 402 403 /* 404 * If the new symbol has PROTECTED visibility, mark it. If a PROTECTED 405 * symbol is copy relocated, a warning message will be printed. See 406 * reloc_exec(). 407 */ 408 if (ELF_ST_VISIBILITY(nsym->st_other) == STV_PROTECTED) 409 sdp->sd_flags |= FLG_SY_PROT; 410 else 411 sdp->sd_flags &= ~FLG_SY_PROT; 412 413 /* 414 * Establish the symbols reference. If the new symbol originates from a 415 * relocatable object then this reference becomes needed, otherwise 416 * the new symbol must be from a shared object. In this case only 417 * promote the symbol to needed if we presently have a reference from a 418 * relocatable object. 419 */ 420 if (ifl->ifl_ehdr->e_type == ET_REL) { 421 sdp->sd_ref = REF_REL_NEED; 422 423 if (nsym->st_shndx == SHN_UNDEF) { 424 /* 425 * If this is an undefined symbol it must be a 426 * relocatable object overriding a shared object. In 427 * this case also override the reference name so that 428 * any undefined symbol diagnostics will refer to the 429 * relocatable object name. 430 */ 431 sdp->sd_aux->sa_rfile = ifl->ifl_name; 432 } else { 433 /* 434 * Under -Bnodirect, all exported interfaces that have 435 * not explicitly been defined protected or directly 436 * bound to, are tagged to prevent direct binding. 437 */ 438 if ((ofl->ofl_flags1 & FLG_OF1_ALNODIR) && 439 ((sdp->sd_flags1 & 440 (FLG_SY1_PROTECT | FLG_SY1_DIR)) == 0)) 441 sdp->sd_flags1 |= FLG_SY1_NDIR; 442 } 443 444 /* 445 * If this symbol is an undefined, or common, determine whether 446 * it is a global or weak reference (see build_osym(), where 447 * REF_DYN_NEED definitions are returned back to undefines). 448 */ 449 if (((nsym->st_shndx == SHN_UNDEF) || 450 ((nsymflags & FLG_SY_SPECSEC) && 451 (nsym->st_shndx == SHN_COMMON))) && 452 (ELF_ST_BIND(nsym->st_info) == STB_GLOBAL)) 453 sdp->sd_flags |= FLG_SY_GLOBREF; 454 else 455 sdp->sd_flags &= ~FLG_SY_GLOBREF; 456 } else { 457 if (sdp->sd_ref == REF_REL_NEED) 458 sdp->sd_ref = REF_DYN_NEED; 459 460 /* 461 * Determine the symbols availability. A symbol is determined 462 * to be unavailable if it belongs to a version of a shared 463 * object that this user does not wish to use, or if it belongs 464 * to an implicit shared object. 465 */ 466 if (ifl->ifl_vercnt) { 467 Ver_index *vip; 468 Half vndx = ifl->ifl_versym[ndx]; 469 470 sdp->sd_aux->sa_dverndx = vndx; 471 vip = &ifl->ifl_verndx[vndx]; 472 if (!(vip->vi_flags & FLG_VER_AVAIL)) { 473 sdp->sd_flags |= FLG_SY_NOTAVAIL; 474 /* 475 * If this is the first occurrence of an 476 * unavailable symbol record it for possible 477 * use in later error diagnostics 478 * (see sym_undef). 479 */ 480 if (!(sdp->sd_aux->sa_vfile)) 481 sdp->sd_aux->sa_vfile = ifl->ifl_name; 482 } 483 } 484 if (!(ifl->ifl_flags & FLG_IF_NEEDED)) 485 sdp->sd_flags |= FLG_SY_NOTAVAIL; 486 } 487 488 /* 489 * Make sure any symbol association maintained by the original symbol 490 * is cleared and then update the symbols file reference. 491 */ 492 if ((link = sdp->sd_aux->sa_linkndx) != 0) { 493 Sym_desc * _sdp; 494 495 _sdp = sdp->sd_file->ifl_oldndx[link]; 496 _sdp->sd_aux->sa_linkndx = 0; 497 sdp->sd_aux->sa_linkndx = 0; 498 } 499 sdp->sd_file = ifl; 500 501 /* 502 * Update the input section descriptor to that of the new input file 503 */ 504 if (((nsymflags & FLG_SY_SPECSEC) == 0) && 505 (nsym->st_shndx != SHN_UNDEF)) { 506 if ((sdp->sd_isc = ifl->ifl_isdesc[nshndx]) == 0) { 507 eprintf(ofl->ofl_lml, ERR_FATAL, 508 MSG_INTL(MSG_SYM_NOSECDEF), demangle(sdp->sd_name), 509 ifl->ifl_name); 510 ofl->ofl_flags |= FLG_OF_FATAL; 511 } 512 } 513 } 514 515 /* 516 * Resolve two undefines (only called for two relocatable objects). 517 */ 518 static void 519 sym_twoundefs(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 520 int ndx, Word nshndx, Word nsymflags) 521 { 522 Sym *osym = sdp->sd_sym; 523 uchar_t obind = ELF_ST_BIND(osym->st_info); 524 uchar_t nbind = ELF_ST_BIND(nsym->st_info); 525 526 /* 527 * If two relocatable objects define a weak and non-weak undefined 528 * reference, take the non-weak definition. 529 * 530 * -- or -- 531 * 532 * If two relocatable objects define a NOTYPE & another, then 533 * take the other. 534 */ 535 if (((obind == STB_WEAK) && (nbind != STB_WEAK)) || 536 (obind == STT_NOTYPE) && (nbind != STT_NOTYPE)) { 537 sym_override(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 538 return; 539 } 540 sym_typecheck(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 541 } 542 543 /* 544 * Resolve two real definitions. 545 */ 546 static void 547 sym_tworeals(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 548 int ndx, Word nshndx, Word nsymflags) 549 { 550 Conv_inv_buf_t inv_buf1, inv_buf2; 551 Sym *osym = sdp->sd_sym; 552 uchar_t otype = ELF_ST_TYPE(osym->st_info); 553 uchar_t obind = ELF_ST_BIND(osym->st_info); 554 uchar_t ntype = ELF_ST_TYPE(nsym->st_info); 555 uchar_t nbind = ELF_ST_BIND(nsym->st_info); 556 Half ofile = sdp->sd_file->ifl_ehdr->e_type; 557 Half nfile = ifl->ifl_ehdr->e_type; 558 int warn = 0; 559 560 /* 561 * If both definitions are from relocatable objects, and have non-weak 562 * binding then this is a fatal condition. 563 */ 564 if ((ofile == ET_REL) && (nfile == ET_REL) && (obind != STB_WEAK) && 565 (nbind != STB_WEAK) && (!(ofl->ofl_flags & FLG_OF_MULDEFS))) { 566 eprintf(ofl->ofl_lml, ERR_FATAL, MSG_INTL(MSG_SYM_MULDEF), 567 demangle(sdp->sd_name)); 568 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_FILETYPES), 569 sdp->sd_file->ifl_name, 570 conv_sym_info_type(ofl->ofl_dehdr->e_machine, otype, 571 0, &inv_buf1), ifl->ifl_name, 572 conv_sym_info_type(ofl->ofl_dehdr->e_machine, ntype, 573 0, &inv_buf2)); 574 ofl->ofl_flags |= FLG_OF_FATAL; 575 return; 576 } 577 578 /* 579 * Perform any machine specific type checking. 580 */ 581 if ((ld_targ.t_ms.ms_mach_sym_typecheck != NULL) && 582 (*ld_targ.t_ms.ms_mach_sym_typecheck)(sdp, nsym, ifl, ofl)) 583 return; 584 585 /* 586 * Check the symbols type and size. 587 */ 588 if (otype != ntype) { 589 eprintf(ofl->ofl_lml, ERR_WARNING, MSG_INTL(MSG_SYM_DIFFTYPE), 590 demangle(sdp->sd_name)); 591 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_FILETYPES), 592 sdp->sd_file->ifl_name, 593 conv_sym_info_type(ofl->ofl_dehdr->e_machine, otype, 594 0, &inv_buf1), ifl->ifl_name, 595 conv_sym_info_type(ofl->ofl_dehdr->e_machine, ntype, 596 0, &inv_buf2)); 597 warn++; 598 } else if ((otype == STT_OBJECT) && (osym->st_size != nsym->st_size)) { 599 if (!(ofl->ofl_flags & FLG_OF_NOWARN)) { 600 eprintf(ofl->ofl_lml, ERR_WARNING, 601 MSG_INTL(MSG_SYM_DIFFATTR), demangle(sdp->sd_name), 602 MSG_INTL(MSG_STR_SIZES), sdp->sd_file->ifl_name, 603 EC_XWORD(osym->st_size), ifl->ifl_name, 604 EC_XWORD(nsym->st_size)); 605 warn++; 606 } 607 } 608 609 /* 610 * Having provided the user with any necessary warnings, take the 611 * appropriate symbol: 612 * 613 * - if one symbol is from a shared object and the other is from a 614 * relocatable object, take the relocatable objects symbol (the 615 * run-time linker is always going to find the relocatable object 616 * symbol regardless of the binding), else 617 * 618 * - if both symbols are from relocatable objects and one symbol is 619 * weak take the non-weak symbol (two non-weak symbols would have 620 * generated the fatal error condition above unless -z muldefs is 621 * in effect), else 622 * 623 * - take the first symbol definition encountered. 624 */ 625 if ((sdp->sd_flags & FLG_SY_SOFOUND) && (nfile == ET_DYN)) { 626 if (warn) 627 eprintf(ofl->ofl_lml, ERR_NONE, 628 MSG_INTL(MSG_SYM_DEFTAKEN), sdp->sd_file->ifl_name); 629 return; 630 } else if ((nfile == ET_REL) && ((ofile == ET_DYN) || 631 ((obind == STB_WEAK) && (nbind != STB_WEAK)))) { 632 if (warn) 633 eprintf(ofl->ofl_lml, ERR_NONE, 634 MSG_INTL(MSG_SYM_DEFTAKEN), ifl->ifl_name); 635 sym_override(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 636 return; 637 } else { 638 if (warn) 639 eprintf(ofl->ofl_lml, ERR_NONE, 640 MSG_INTL(MSG_SYM_DEFTAKEN), sdp->sd_file->ifl_name); 641 sym_promote(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 642 return; 643 } 644 } 645 646 /* 647 * Resolve a real and tentative definition. 648 */ 649 static void 650 sym_realtent(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 651 int ndx, Word nshndx, Word nsymflags) 652 { 653 Conv_inv_buf_t inv_buf1, inv_buf2; 654 Sym *osym = sdp->sd_sym; 655 uchar_t otype = ELF_ST_TYPE(osym->st_info); 656 uchar_t obind = ELF_ST_BIND(osym->st_info); 657 uchar_t ntype = ELF_ST_TYPE(nsym->st_info); 658 uchar_t nbind = ELF_ST_BIND(nsym->st_info); 659 Boolean otent = FALSE, ntent = FALSE; 660 Half ofile = sdp->sd_file->ifl_ehdr->e_type; 661 Half nfile = ifl->ifl_ehdr->e_type; 662 int warn = 0; 663 uchar_t ovis = ELF_ST_VISIBILITY(osym->st_other); 664 uchar_t nvis = ELF_ST_VISIBILITY(nsym->st_other); 665 666 /* 667 * Special rules for functions. 668 * 669 * - If both definitions are from relocatable objects, have the same 670 * binding (ie. two weaks or two non-weaks), and the real 671 * definition is a function (the other must be tentative), treat 672 * this as a multiply defined symbol error, else 673 * 674 * - if the real symbol definition is a function within a shared 675 * library and the tentative symbol is a relocatable object, and 676 * the tentative is not weak and the function real, then retain the 677 * tentative definition. 678 */ 679 if ((ofile == ET_REL) && (nfile == ET_REL) && (obind == nbind) && 680 ((otype == STT_FUNC) || (ntype == STT_FUNC))) { 681 if (ofl->ofl_flags & FLG_OF_MULDEFS) { 682 eprintf(ofl->ofl_lml, ERR_WARNING, 683 MSG_INTL(MSG_SYM_DIFFTYPE), demangle(sdp->sd_name)); 684 sym_promote(sdp, nsym, ifl, ofl, ndx, 685 nshndx, nsymflags); 686 } else { 687 eprintf(ofl->ofl_lml, ERR_FATAL, 688 MSG_INTL(MSG_SYM_MULDEF), demangle(sdp->sd_name)); 689 ofl->ofl_flags |= FLG_OF_FATAL; 690 } 691 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_FILETYPES), 692 sdp->sd_file->ifl_name, 693 conv_sym_info_type(ofl->ofl_dehdr->e_machine, otype, 694 0, &inv_buf1), ifl->ifl_name, 695 conv_sym_info_type(ofl->ofl_dehdr->e_machine, ntype, 696 0, &inv_buf2)); 697 return; 698 } else if (ofile != nfile) { 699 700 701 if ((ofile == ET_DYN) && (otype == STT_FUNC)) { 702 if ((otype != STB_WEAK) && (ntype == STB_WEAK)) 703 return; 704 else { 705 sym_override(sdp, nsym, ifl, ofl, ndx, 706 nshndx, nsymflags); 707 return; 708 } 709 } 710 if ((nfile == ET_DYN) && (ntype == STT_FUNC)) { 711 if ((ntype != STB_WEAK) && (otype == STB_WEAK)) { 712 sym_override(sdp, nsym, ifl, ofl, ndx, 713 nshndx, nsymflags); 714 return; 715 } else 716 return; 717 } 718 } 719 720 if (sdp->sd_flags & FLG_SY_TENTSYM) 721 otent = TRUE; 722 if (nsymflags & FLG_SY_TENTSYM) 723 ntent = TRUE; 724 725 726 /* 727 * Check the symbols type and size. 728 */ 729 if (otype != ntype) { 730 eprintf(ofl->ofl_lml, ERR_WARNING, MSG_INTL(MSG_SYM_DIFFTYPE), 731 demangle(sdp->sd_name)); 732 eprintf(ofl->ofl_lml, ERR_NONE, MSG_INTL(MSG_SYM_FILETYPES), 733 sdp->sd_file->ifl_name, 734 conv_sym_info_type(ofl->ofl_dehdr->e_machine, otype, 735 0, &inv_buf1), ifl->ifl_name, 736 conv_sym_info_type(ofl->ofl_dehdr->e_machine, ntype, 737 0, &inv_buf2)); 738 warn++; 739 } else if (osym->st_size != nsym->st_size) { 740 /* 741 * If both definitions are from relocatable objects we have a 742 * potential fatal error condition. If the tentative is larger 743 * than the real definition treat this as a multiple definition. 744 * Note that if only one symbol is weak, the non-weak will be 745 * taken. 746 */ 747 if (((ofile == ET_REL) && (nfile == ET_REL) && 748 (obind == nbind)) && 749 ((otent && (osym->st_size > nsym->st_size)) || 750 (ntent && (osym->st_size < nsym->st_size)))) { 751 eprintf(ofl->ofl_lml, ERR_FATAL, 752 MSG_INTL(MSG_SYM_DIFFATTR), demangle(sdp->sd_name), 753 MSG_INTL(MSG_STR_SIZES), sdp->sd_file->ifl_name, 754 EC_XWORD(osym->st_size), ifl->ifl_name, 755 EC_XWORD(nsym->st_size)); 756 eprintf(ofl->ofl_lml, ERR_NONE, 757 MSG_INTL(MSG_SYM_TENTERR)); 758 ofl->ofl_flags |= FLG_OF_FATAL; 759 } else { 760 if (!(ofl->ofl_flags & FLG_OF_NOWARN)) { 761 eprintf(ofl->ofl_lml, ERR_WARNING, 762 MSG_INTL(MSG_SYM_DIFFATTR), 763 demangle(sdp->sd_name), 764 MSG_INTL(MSG_STR_SIZES), 765 sdp->sd_file->ifl_name, 766 EC_XWORD(osym->st_size), 767 ifl->ifl_name, EC_XWORD(nsym->st_size)); 768 warn++; 769 } 770 } 771 } 772 773 /* 774 * Having provided the user with any necessary warnings, take the 775 * appropriate symbol: 776 * 777 * - if the original symbol is from relocatable file and it is 778 * a protected tentative symbol, take the original one. 779 * 780 * - if the original symbol is from shared object and the new 781 * symbol is a protected tentative symbol from a relocatable file, 782 * take the new one. 783 * 784 * - if the original symbol is tentative, and providing the original 785 * symbol isn't strong and the new symbol weak, take the real 786 * symbol, else 787 * 788 * - if the original symbol is weak and the new tentative symbol is 789 * strong take the new symbol. 790 * 791 * Refer to the System V ABI Page 4-27 for a description of the binding 792 * requirements of tentative and weak symbols. 793 */ 794 if ((ofile == ET_REL) && (nfile == ET_DYN) && (otent == TRUE) && 795 (ovis == STV_PROTECTED)) { 796 return; 797 } 798 799 if ((ofile == ET_DYN) && (nfile == ET_REL) && (ntent == TRUE) && 800 (nvis == STV_PROTECTED)) { 801 sym_override(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 802 return; 803 } 804 805 if ((sdp->sd_flags & FLG_SY_SOFOUND) && (nfile == ET_DYN)) { 806 if (warn) 807 eprintf(ofl->ofl_lml, ERR_NONE, 808 MSG_INTL(MSG_SYM_DEFTAKEN), sdp->sd_file->ifl_name); 809 return; 810 } 811 812 if (((otent) && (!((obind != STB_WEAK) && (nbind == STB_WEAK)))) || 813 ((obind == STB_WEAK) && (nbind != STB_WEAK))) { 814 if (warn) 815 eprintf(ofl->ofl_lml, ERR_NONE, 816 MSG_INTL(MSG_SYM_DEFTAKEN), ifl->ifl_name); 817 sym_override(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 818 return; 819 } else { 820 if (warn) 821 eprintf(ofl->ofl_lml, ERR_NONE, 822 MSG_INTL(MSG_SYM_DEFTAKEN), sdp->sd_file->ifl_name); 823 sym_promote(sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 824 return; 825 } 826 } 827 828 /* 829 * Resolve two tentative symbols. 830 */ 831 static void 832 sym_twotent(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, 833 int ndx, Word nshndx, Word nsymflags) 834 { 835 Sym *osym = sdp->sd_sym; 836 uchar_t obind = ELF_ST_BIND(osym->st_info); 837 uchar_t nbind = ELF_ST_BIND(nsym->st_info); 838 Half ofile = sdp->sd_file->ifl_ehdr->e_type; 839 Half nfile = ifl->ifl_ehdr->e_type; 840 size_t size = 0; 841 Xword value = 0; 842 843 #if defined(_ELF64) 844 if (ld_targ.t_m.m_mach == EM_AMD64) { 845 /* 846 * If the original and new symbols are both COMMON, but of 847 * a different size model, take the small one. 848 */ 849 if ((sdp->sd_sym->st_shndx == SHN_COMMON) && 850 (nsym->st_shndx == SHN_X86_64_LCOMMON)) { 851 /* 852 * Take the original symbol. 853 */ 854 return; 855 856 } else if ((sdp->sd_sym->st_shndx == SHN_X86_64_LCOMMON) && 857 (nsym->st_shndx == SHN_COMMON)) { 858 /* 859 * Take the new symbol. 860 */ 861 sym_override(sdp, nsym, ifl, ofl, ndx, nshndx, 862 nsymflags); 863 return; 864 } 865 } 866 #endif 867 868 /* 869 * Check the alignment of the symbols. This can only be tested for if 870 * the symbols are not real definitions to a SHT_NOBITS section (ie. 871 * they were originally tentative), as in this case the symbol would 872 * have a displacement value rather than an alignment. In other words 873 * we can only test this for two relocatable objects. 874 */ 875 /* BEGIN CSTYLED */ 876 if ((osym->st_value != nsym->st_value) && 877 ((sdp->sd_flags & FLG_SY_SPECSEC) && 878 (sdp->sd_sym->st_shndx == SHN_COMMON) && 879 (nsymflags & FLG_SY_SPECSEC) && 880 #if defined(_ELF64) 881 (nsym->st_shndx == SHN_COMMON)) || 882 ((ld_targ.t_m.m_mach == EM_AMD64) && 883 (sdp->sd_flags & FLG_SY_SPECSEC) && 884 (sdp->sd_sym->st_shndx == SHN_X86_64_LCOMMON) && 885 (nsymflags & FLG_SY_SPECSEC) && 886 (nsym->st_shndx == SHN_X86_64_LCOMMON))) { 887 #else 888 (nsym->st_shndx == SHN_COMMON))) { 889 #endif 890 /* END CSTYLED */ 891 892 const char *emsg = MSG_INTL(MSG_SYM_DEFTAKEN); 893 const char *file; 894 Xword salign; 895 Xword balign; 896 uint_t alignscompliment; 897 898 if (osym->st_value < nsym->st_value) { 899 salign = osym->st_value; 900 balign = nsym->st_value; 901 } else { 902 salign = nsym->st_value; 903 balign = osym->st_value; 904 } 905 906 /* 907 * If the smaller alignment fits smoothly into the 908 * larger alignment - we take it with no warning. 909 */ 910 if (S_ALIGN(balign, salign) == balign) 911 alignscompliment = 1; 912 else 913 alignscompliment = 0; 914 915 if (!(ofl->ofl_flags & FLG_OF_NOWARN) && !alignscompliment) 916 eprintf(ofl->ofl_lml, ERR_WARNING, 917 MSG_INTL(MSG_SYM_DIFFATTR), demangle(sdp->sd_name), 918 MSG_INTL(MSG_STR_ALIGNMENTS), 919 sdp->sd_file->ifl_name, EC_XWORD(osym->st_value), 920 ifl->ifl_name, EC_XWORD(nsym->st_value)); 921 922 /* 923 * Having provided the necessary warning indicate which 924 * relocatable object we are going to take. 925 * 926 * - if one symbol is weak and the other is non-weak 927 * take the non-weak symbol, else 928 * 929 * - take the largest alignment (as we still have to check 930 * the symbols size simply save the largest value for 931 * updating later). 932 */ 933 if ((obind == STB_WEAK) && (nbind != STB_WEAK)) 934 file = ifl->ifl_name; 935 else if (obind != nbind) 936 file = sdp->sd_file->ifl_name; 937 else { 938 emsg = MSG_INTL(MSG_SYM_LARGER); 939 value = balign; 940 } 941 if (!(ofl->ofl_flags & FLG_OF_NOWARN) && !alignscompliment) 942 eprintf(ofl->ofl_lml, ERR_NONE, emsg, file); 943 } 944 945 /* 946 * Check the size of the symbols. 947 */ 948 if (osym->st_size != nsym->st_size) { 949 const char *emsg = MSG_INTL(MSG_SYM_DEFTAKEN); 950 const char *file; 951 952 if (!(ofl->ofl_flags & FLG_OF_NOWARN)) 953 eprintf(ofl->ofl_lml, ERR_WARNING, 954 MSG_INTL(MSG_SYM_DIFFATTR), demangle(sdp->sd_name), 955 MSG_INTL(MSG_STR_SIZES), sdp->sd_file->ifl_name, 956 EC_XWORD(osym->st_size), ifl->ifl_name, 957 EC_XWORD(nsym->st_size)); 958 959 960 /* 961 * This symbol has already been compared to an SO definition, 962 * as per the runtime behavior, ignore extra definitions. 963 */ 964 if ((sdp->sd_flags & FLG_SY_SOFOUND) && (nfile == ET_DYN)) { 965 if (!(ofl->ofl_flags & FLG_OF_NOWARN)) 966 eprintf(ofl->ofl_lml, ERR_NONE, emsg, 967 sdp->sd_file->ifl_name); 968 return; 969 } 970 971 /* 972 * Having provided the necessary warning indicate what course 973 * of action we are going to take. 974 * 975 * - if the file types differ, take the relocatable object 976 * and apply the largest symbol size, else 977 * - if one symbol is weak and the other is non-weak, take 978 * the non-weak symbol, else 979 * - simply take the largest symbol reference. 980 */ 981 if (nfile != ofile) { 982 if (nfile == ET_REL) { 983 file = ifl->ifl_name; 984 if (osym->st_size > nsym->st_size) { 985 size = (size_t)osym->st_size; 986 emsg = MSG_INTL(MSG_SYM_DEFUPDATE); 987 } 988 sym_override(sdp, nsym, ifl, ofl, ndx, 989 nshndx, nsymflags); 990 } else { 991 file = sdp->sd_file->ifl_name; 992 if (osym->st_size < nsym->st_size) { 993 size = (size_t)nsym->st_size; 994 emsg = MSG_INTL(MSG_SYM_DEFUPDATE); 995 } 996 sym_promote(sdp, nsym, ifl, ofl, ndx, 997 nshndx, nsymflags); 998 } 999 } else if (obind != nbind) { 1000 if ((obind == STB_WEAK) && (nbind != STB_WEAK)) { 1001 sym_override(sdp, nsym, ifl, ofl, ndx, 1002 nshndx, nsymflags); 1003 file = ifl->ifl_name; 1004 } else 1005 file = sdp->sd_file->ifl_name; 1006 } else { 1007 if (osym->st_size < nsym->st_size) { 1008 sym_override(sdp, nsym, ifl, ofl, ndx, 1009 nshndx, nsymflags); 1010 file = ifl->ifl_name; 1011 } else 1012 file = sdp->sd_file->ifl_name; 1013 } 1014 if (!(ofl->ofl_flags & FLG_OF_NOWARN)) 1015 eprintf(ofl->ofl_lml, ERR_NONE, emsg, file); 1016 if (size) 1017 sdp->sd_sym->st_size = (Xword)size; 1018 } else { 1019 /* 1020 * If the sizes are the same 1021 * 1022 * - if the file types differ, take the relocatable object, 1023 * else 1024 * 1025 * - if one symbol is weak and the other is non-weak, take 1026 * the non-weak symbol, else 1027 * 1028 * - take the first reference. 1029 */ 1030 if ((sdp->sd_flags & FLG_SY_SOFOUND) && (nfile == ET_DYN)) 1031 return; 1032 else if (((ofile != nfile) && (nfile == ET_REL)) || 1033 (((obind == STB_WEAK) && (nbind != STB_WEAK)) && 1034 (!((ofile != nfile) && (ofile == ET_REL))))) 1035 sym_override(sdp, nsym, ifl, ofl, ndx, 1036 nshndx, nsymflags); 1037 else 1038 sym_promote(sdp, nsym, ifl, ofl, ndx, 1039 nshndx, nsymflags); 1040 } 1041 1042 /* 1043 * Enforce the largest alignment if necessary. 1044 */ 1045 if (value) 1046 sdp->sd_sym->st_value = value; 1047 } 1048 1049 /* 1050 * Symbol resolution state table. `Action' describes the required 1051 * procedure to be called (if any). 1052 */ 1053 static void (*Action[REF_NUM * SYM_NUM * 2][SYM_NUM])(Sym_desc *, 1054 Sym *, Ifl_desc *, Ofl_desc *, int, Word, Word) = { 1055 1056 /* defined undef tent */ 1057 /* ET_REL ET_REL ET_REL */ 1058 1059 /* 0 defined REF_DYN_SEEN */ sym_tworeals, sym_promote, sym_realtent, 1060 /* 1 undef REF_DYN_SEEN */ sym_override, sym_override, sym_override, 1061 /* 2 tent REF_DYN_SEEN */ sym_realtent, sym_promote, sym_twotent, 1062 /* 3 defined REF_DYN_NEED */ sym_tworeals, sym_typecheck, sym_realtent, 1063 /* 4 undef REF_DYN_NEED */ sym_override, sym_override, sym_override, 1064 /* 5 tent REF_DYN_NEED */ sym_realtent, sym_typecheck, sym_twotent, 1065 /* 6 defined REF_REL_NEED */ sym_tworeals, sym_typecheck, sym_realtent, 1066 /* 7 undef REF_REL_NEED */ sym_override, sym_twoundefs, sym_override, 1067 /* 8 tent REF_REL_NEED */ sym_realtent, sym_null, sym_twotent, 1068 1069 /* defined undef tent */ 1070 /* ET_DYN ET_DYN ET_DYN */ 1071 1072 /* 9 defined REF_DYN_SEEN */ sym_tworeals, sym_null, sym_realtent, 1073 /* 10 undef REF_DYN_SEEN */ sym_override, sym_mach_check, sym_override, 1074 /* 11 tent REF_DYN_SEEN */ sym_realtent, sym_null, sym_twotent, 1075 /* 12 defined REF_DYN_NEED */ sym_tworeals, sym_null, sym_realtent, 1076 /* 13 undef REF_DYN_NEED */ sym_override, sym_null, sym_override, 1077 /* 14 tent REF_DYN_NEED */ sym_realtent, sym_null, sym_twotent, 1078 /* 15 defined REF_REL_NEED */ sym_tworeals, sym_null, sym_realtent, 1079 /* 16 undef REF_REL_NEED */ sym_override, sym_mach_check, sym_override, 1080 /* 17 tent REF_REL_NEED */ sym_realtent, sym_null, sym_twotent 1081 1082 }; 1083 1084 uintptr_t 1085 ld_sym_resolve(Sym_desc *sdp, Sym *nsym, Ifl_desc *ifl, Ofl_desc *ofl, int ndx, 1086 Word nshndx, Word nsymflags) 1087 { 1088 int row, column; /* State table coordinates */ 1089 Sym *osym = sdp->sd_sym; 1090 Is_desc *isp; 1091 Half vis = 0, nfile = ifl->ifl_ehdr->e_type; 1092 Half oref = sdp->sd_ref; 1093 1094 /* 1095 * Determine the original symbols definition (defines row in Action[]). 1096 */ 1097 if (sdp->sd_flags & FLG_SY_TENTSYM) 1098 row = SYM_TENTATIVE; 1099 else if ((sdp->sd_sym->st_shndx == SHN_UNDEF) || 1100 (sdp->sd_sym->st_shndx == SHN_SUNW_IGNORE)) 1101 row = SYM_UNDEFINED; 1102 else 1103 row = SYM_DEFINED; 1104 1105 /* 1106 * If the input file is an implicit shared object then we don't need 1107 * to bind to any symbols within it other than to verify that any 1108 * undefined references will be closed (implicit shared objects are only 1109 * processed when no undefined symbols are required as a result of the 1110 * link-edit (see process_dynamic())). 1111 */ 1112 if ((nfile == ET_DYN) && !(ifl->ifl_flags & FLG_IF_NEEDED) && 1113 (row != SYM_UNDEFINED)) 1114 return (1); 1115 1116 /* 1117 * Finish computing the Action[] row by applying the symbols reference 1118 * together with the input files type. 1119 */ 1120 row = row + (REF_NUM * sdp->sd_ref); 1121 if (nfile == ET_DYN) 1122 row += (REF_NUM * SYM_NUM); 1123 1124 /* 1125 * If either the original or new symbol originates from a relocatable 1126 * object, determine the appropriate visibility for the resolved symbol. 1127 */ 1128 if ((oref == REF_REL_NEED) || (nfile == ET_REL)) 1129 vis = sym_visibility(sdp, nsym, ifl, ofl); 1130 1131 /* 1132 * Determine the new symbols definition (defines column in Action[]). 1133 */ 1134 if ((nsymflags & FLG_SY_SPECSEC) && 1135 (nsym->st_shndx == SHN_COMMON)) { 1136 column = SYM_TENTATIVE; 1137 nsymflags |= FLG_SY_TENTSYM; 1138 #if defined(_ELF64) 1139 } else if ((ld_targ.t_m.m_mach == EM_AMD64) && 1140 (nsymflags & FLG_SY_SPECSEC) && 1141 (nsym->st_shndx == SHN_X86_64_LCOMMON)) { 1142 column = SYM_TENTATIVE; 1143 nsymflags |= FLG_SY_TENTSYM; 1144 #endif 1145 } else if ((nsym->st_shndx == SHN_UNDEF) || 1146 (nsym->st_shndx == SHN_SUNW_IGNORE)) { 1147 column = SYM_UNDEFINED; 1148 nshndx = SHN_UNDEF; 1149 } else { 1150 column = SYM_DEFINED; 1151 /* 1152 * If the new symbol is from a shared library and it is 1153 * associated with a SHT_NOBITS section then this symbol 1154 * originated from a tentative symbol. 1155 */ 1156 if (((nsymflags & FLG_SY_SPECSEC) == 0) && (nfile == ET_DYN)) { 1157 isp = ifl->ifl_isdesc[nshndx]; 1158 if (isp && (isp->is_shdr->sh_type == SHT_NOBITS)) { 1159 column = SYM_TENTATIVE; 1160 nsymflags |= FLG_SY_TENTSYM; 1161 } 1162 } 1163 } 1164 1165 DBG_CALL(Dbg_syms_resolving(ofl, ndx, sdp->sd_name, row, column, 1166 osym, nsym, sdp, ifl)); 1167 1168 /* 1169 * Record the input filename on the defined files list for possible 1170 * later diagnostics. The `sa_dfiles' list is used to maintain the list 1171 * of shared objects that define the same symbol. This list is only 1172 * generated when the -m option is in effect and is used to list 1173 * multiple (interposed) definitions of a symbol (refer to ldmap_out()). 1174 */ 1175 if ((ofl->ofl_flags & FLG_OF_GENMAP) && (nsym->st_shndx != SHN_UNDEF) && 1176 ((nsymflags & FLG_SY_SPECSEC) == 0)) 1177 if (aplist_append(&sdp->sd_aux->sa_dfiles, ifl->ifl_name, 1178 AL_CNT_SDP_DFILES) == NULL) 1179 return (S_ERROR); 1180 1181 /* 1182 * Perform the required resolution. 1183 */ 1184 Action[row][column](sdp, nsym, ifl, ofl, ndx, nshndx, nsymflags); 1185 1186 /* 1187 * Apply any visibility requirements. If a SINGLETON has been 1188 * established, make sure no symbol reduction indicators remain 1189 * associated with the symbol, and indicate that the symbol can not 1190 * be directly bound to. 1191 */ 1192 if ((oref == REF_REL_NEED) || (nfile == ET_REL)) { 1193 if ((vis == STV_EXPORTED) || (vis == STV_SINGLETON)) { 1194 sdp->sd_flags1 &= ~(FLG_SY1_PROTECT | FLG_SY1_ELIM | 1195 FLG_SY1_HIDDEN); 1196 1197 if (vis == STV_EXPORTED) 1198 sdp->sd_flags1 |= FLG_SY1_EXPORT; 1199 else { 1200 sdp->sd_flags1 |= 1201 (FLG_SY1_NDIR | FLG_SY1_SINGLE); 1202 1203 if (sdp->sd_ref == REF_REL_NEED) { 1204 ofl->ofl_flags1 |= 1205 (FLG_OF1_NDIRECT | FLG_OF1_NGLBDIR); 1206 } 1207 } 1208 } else if (vis == STV_PROTECTED) { 1209 sdp->sd_flags1 |= FLG_SY1_PROTECT; 1210 } else if ((vis == STV_INTERNAL) || (vis == STV_HIDDEN)) { 1211 sdp->sd_flags1 |= FLG_SY1_HIDDEN; 1212 } else if (vis == STV_ELIMINATE) { 1213 sdp->sd_flags1 |= (FLG_SY1_HIDDEN | FLG_SY1_ELIM); 1214 } 1215 1216 sdp->sd_sym->st_other = 1217 (sdp->sd_sym->st_other & ~MSK_SYM_VISIBILITY) | vis; 1218 } 1219 1220 /* 1221 * If the symbol has been resolved to the new input file, and this is 1222 * a versioned relocatable object, then the version information of the 1223 * new symbol must be promoted to the versioning of the output file. 1224 */ 1225 if ((sdp->sd_file == ifl) && (nfile == ET_REL) && (ifl->ifl_versym) && 1226 (nsym->st_shndx != SHN_UNDEF)) 1227 ld_vers_promote(sdp, ndx, ifl, ofl); 1228 1229 /* 1230 * Determine whether a mapfile reference has been satisfied. Mapfile 1231 * symbol references augment symbols that should be contributed from 1232 * the relocatable objects used to build the output image. If a 1233 * relocatable object doesn't provide one of the mapfile symbol 1234 * references then somethings amiss, and will be flagged during symbol 1235 * validation. 1236 */ 1237 if ((nfile == ET_REL) && ((sdp->sd_flags & 1238 (FLG_SY_MAPREF | FLG_SY_MAPUSED)) == FLG_SY_MAPREF)) { 1239 /* 1240 * Extern and parent references are satisfied by references from 1241 * a relocatable object. Note that we let *any* symbol type 1242 * satisfy this reference, to be as flexible as possible with 1243 * user written mapfiles. It could be questionable, for 1244 * example, if what a user expects to be an extern reference is 1245 * actually found to be a definition in a relocatable object. 1246 * 1247 * Any other mapfile reference (typically for versioning 1248 * information) simply augments a relocatables definition. 1249 */ 1250 if ((sdp->sd_flags & (FLG_SY_EXTERN | FLG_SY_PARENT)) || 1251 ((sdp->sd_sym->st_shndx != SHN_UNDEF) && 1252 (sdp->sd_ref == REF_REL_NEED))) 1253 sdp->sd_flags |= FLG_SY_MAPUSED; 1254 } 1255 1256 DBG_CALL(Dbg_syms_resolved(ofl, sdp)); 1257 1258 return (1); 1259 } 1260