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 * Library processing 32 */ 33 #include <stdio.h> 34 #include <string.h> 35 #include <debug.h> 36 #include "msg.h" 37 #include "_libld.h" 38 39 /* 40 * Archive members are typically extracted to resolve an existing undefined 41 * reference. However, other symbol definitions can cause archive members to 42 * be processed to determine if the archive member provides a more appropriate 43 * definition. This routine processes the archive member to determine if the 44 * member is really required. 45 * 46 * i. Tentative symbols may cause the extraction of an archive member. 47 * If the archive member has a strong defined symbol it will be used. 48 * If the archive member simply contains another tentative definition, 49 * or a defined function symbol, then it will not be used. 50 * 51 * ii. A symbol reference may define a hidden or protected visibility. The 52 * reference can only be bound to a definition within a relocatable object 53 * for this restricted visibility to be satisfied. If the archive member 54 * provides a definition of the same symbol type, this definition is 55 * taken. The visibility of the defined symbol is irrelevant, as the most 56 * restrictive visibility of the reference and the definition will be 57 * applied to the final symbol. 58 */ 59 static int 60 process_member(Ar_mem *amp, const char *name, Sym_desc *sdp, Ofl_desc *ofl) 61 { 62 Sym *syms, *osym = sdp->sd_sym; 63 Xword symn, cnt; 64 char *strs; 65 66 /* 67 * Find the first symbol table in the archive member, obtain its 68 * data buffer and determine the number of global symbols (Note, 69 * there must be a symbol table present otherwise the archive would 70 * never have been able to generate its own symbol entry for this 71 * member). 72 */ 73 if (amp->am_syms == 0) { 74 Elf_Scn *scn = NULL; 75 Shdr *shdr; 76 Elf_Data *data; 77 78 while (scn = elf_nextscn(amp->am_elf, scn)) { 79 if ((shdr = elf_getshdr(scn)) == NULL) { 80 eprintf(ofl->ofl_lml, ERR_ELF, 81 MSG_INTL(MSG_ELF_GETSHDR), amp->am_path); 82 ofl->ofl_flags |= FLG_OF_FATAL; 83 return (0); 84 } 85 if ((shdr->sh_type == SHT_SYMTAB) || 86 (shdr->sh_type == SHT_DYNSYM)) 87 break; 88 } 89 if ((data = elf_getdata(scn, NULL)) == NULL) { 90 eprintf(ofl->ofl_lml, ERR_ELF, 91 MSG_INTL(MSG_ELF_GETDATA), amp->am_path); 92 ofl->ofl_flags |= FLG_OF_FATAL; 93 return (0); 94 } 95 syms = (Sym *)data->d_buf; 96 syms += shdr->sh_info; 97 symn = shdr->sh_size / shdr->sh_entsize; 98 symn -= shdr->sh_info; 99 100 /* 101 * Get the data for the associated string table. 102 */ 103 if ((scn = elf_getscn(amp->am_elf, (size_t)shdr->sh_link)) == 104 NULL) { 105 eprintf(ofl->ofl_lml, ERR_ELF, 106 MSG_INTL(MSG_ELF_GETSCN), amp->am_path); 107 ofl->ofl_flags |= FLG_OF_FATAL; 108 return (0); 109 } 110 if ((data = elf_getdata(scn, NULL)) == NULL) { 111 eprintf(ofl->ofl_lml, ERR_ELF, 112 MSG_INTL(MSG_ELF_GETDATA), amp->am_path); 113 ofl->ofl_flags |= FLG_OF_FATAL; 114 return (0); 115 } 116 strs = data->d_buf; 117 118 /* 119 * Initialize the archive member structure in case we have to 120 * come through here again. 121 */ 122 amp->am_syms = syms; 123 amp->am_strs = strs; 124 amp->am_symn = symn; 125 } else { 126 syms = amp->am_syms; 127 strs = amp->am_strs; 128 symn = amp->am_symn; 129 } 130 131 /* 132 * Loop through the symbol table entries looking for a match for the 133 * original symbol. 134 */ 135 for (cnt = 0; cnt < symn; syms++, cnt++) { 136 Word shndx; 137 138 if ((shndx = syms->st_shndx) == SHN_UNDEF) 139 continue; 140 141 if (osym->st_shndx == SHN_COMMON) { 142 /* 143 * Determine whether a tentative symbol definition 144 * should be overridden. 145 */ 146 if ((shndx == SHN_ABS) || (shndx == SHN_COMMON) || 147 (ELF_ST_TYPE(syms->st_info) == STT_FUNC)) 148 continue; 149 150 /* 151 * A historic detail requires that a weak definition 152 * within an archive will not override a strong 153 * definition (see sym_realtent() resolution and ABI 154 * symbol binding description - page 4-27). 155 */ 156 if ((ELF_ST_BIND(syms->st_info) == STB_WEAK) && 157 (ELF_ST_BIND(osym->st_info) != STB_WEAK)) 158 continue; 159 } else { 160 /* 161 * Determine whether a restricted visibility reference 162 * should be overridden. Don't worry about the 163 * visibility of the archive member definition, nor 164 * whether it is weak or global. Any definition is 165 * better than a binding to an external shared object 166 * (which is the only event that must presently exist 167 * for us to be here looking for a better alternative). 168 */ 169 if (ELF_ST_TYPE(syms->st_info) != 170 ELF_ST_TYPE(osym->st_info)) 171 continue; 172 } 173 174 if (strcmp(strs + syms->st_name, name) == NULL) 175 return (1); 176 } 177 return (0); 178 } 179 180 /* 181 * Create an archive descriptor. By maintaining a list of archives any 182 * duplicate occurrences of the same archive specified by the user enable us to 183 * pick off where the last processing finished. 184 */ 185 Ar_desc * 186 ld_ar_setup(const char *name, Elf *elf, Ofl_desc *ofl) 187 { 188 Ar_desc * adp; 189 size_t number; 190 Elf_Arsym * start; 191 192 /* 193 * Get the archive symbol table. If this fails, we will 194 * ignore this file with a warning message. 195 */ 196 if ((start = elf_getarsym(elf, &number)) == 0) { 197 if (elf_errno()) { 198 eprintf(ofl->ofl_lml, ERR_ELF, 199 MSG_INTL(MSG_ELF_GETARSYM), name); 200 ofl->ofl_flags |= FLG_OF_FATAL; 201 } else 202 eprintf(ofl->ofl_lml, ERR_WARNING, 203 MSG_INTL(MSG_ELF_ARSYM), name); 204 205 return (0); 206 } 207 208 /* 209 * As this is a new archive reference establish a new descriptor. 210 */ 211 if ((adp = libld_malloc(sizeof (Ar_desc))) == 0) 212 return ((Ar_desc *)S_ERROR); 213 adp->ad_name = name; 214 adp->ad_elf = elf; 215 adp->ad_start = start; 216 if ((adp->ad_aux = libld_calloc(sizeof (Ar_aux), number)) == 0) 217 return ((Ar_desc *)S_ERROR); 218 219 /* 220 * Retain any command line options that are applicable to archive 221 * extraction in case we have to rescan this archive later. 222 */ 223 adp->ad_flags = ofl->ofl_flags1 & MSK_OF1_ARCHIVE; 224 225 ofl->ofl_arscnt++; 226 227 /* 228 * Add this new descriptor to the list of archives. 229 */ 230 if (list_appendc(&ofl->ofl_ars, adp) == 0) 231 return ((Ar_desc *)S_ERROR); 232 else 233 return (adp); 234 } 235 236 /* 237 * For each archive descriptor, maintain an `Ar_aux' table to parallel the 238 * archive symbol table (returned from elf_getarsym(3e)). Use this table to 239 * hold a `Sym_desc' for each symbol (thus reducing the number of 240 * ld_sym_find()'s), and to hold the `Ar_mem' pointer. The `Ar_mem' element 241 * can have one of three values indicating the state of the archive member 242 * associated with the offset for this symbol table entry: 243 * 244 * 0 indicates that the member has not been processed. 245 * 246 * FLG_ARMEM_PROC 247 * indicates that the member has been processed. 248 * 249 * addr indicates that the member has been investigated to determine if 250 * it contained a symbol definition we need, but was found not to 251 * be a candidate for extraction. In this case the members 252 * structure is maintained for possible later use. 253 * 254 * Each time we process an archive member we use its offset value to scan this 255 * `Ar_aux' list. If the member has been extracted, each entry with the same 256 * offset has its `Ar_mem' pointer set to FLG_ARMEM_PROC. Thus if we cycle back 257 * through the archive symbol table we will ignore these symbols as they will 258 * have already been added to the output image. If a member has been processed 259 * but found not to contain a symbol we need, each entry with the same offset 260 * has its `Ar_mem' pointer set to the member structures address. 261 */ 262 void 263 ld_ar_member(Ar_desc * adp, Elf_Arsym * arsym, Ar_aux * aup, Ar_mem * amp) 264 { 265 Elf_Arsym * _arsym = arsym; 266 Ar_aux * _aup = aup; 267 size_t _off = arsym->as_off; 268 269 if (_arsym != adp->ad_start) { 270 do { 271 _arsym--; 272 _aup--; 273 if (_arsym->as_off != _off) 274 break; 275 _aup->au_mem = amp; 276 } while (_arsym != adp->ad_start); 277 } 278 279 _arsym = arsym; 280 _aup = aup; 281 282 do { 283 if (_arsym->as_off != _off) 284 break; 285 _aup->au_mem = amp; 286 _arsym++; 287 _aup++; 288 } while (_arsym->as_name); 289 } 290 291 /* 292 * Data structure to indicate whether a symbol is visible for the purpose 293 * of archive extraction. 294 */ 295 static const Boolean 296 sym_vis[STV_NUM] = { 297 TRUE, /* STV_DEFAULT */ 298 FALSE, /* STV_INTERNAL */ 299 FALSE, /* STV_HIDDEN */ 300 FALSE, /* STV_PROTECTED */ 301 TRUE, /* STV_EXPORTED */ 302 TRUE, /* STV_SINGLETON */ 303 FALSE /* STV_ELIMINATE */ 304 }; 305 #if STV_NUM != (STV_ELIMINATE + 1) 306 #error "STV_NUM has grown. Update sym_vis[]." 307 #endif 308 309 /* 310 * Read the archive symbol table. For each symbol in the table, determine 311 * whether that symbol satisfies an unresolved reference, tentative reference, 312 * or a reference that expects hidden or protected visibility. If so, the 313 * corresponding object from the archive is processed. The archive symbol 314 * table is searched until we go through a complete pass without satisfying any 315 * unresolved symbols 316 */ 317 uintptr_t 318 ld_process_archive(const char *name, int fd, Ar_desc *adp, Ofl_desc *ofl) 319 { 320 Elf_Arsym * arsym; 321 Elf_Arhdr * arhdr; 322 Elf * arelf; 323 Ar_aux * aup; 324 Sym_desc * sdp; 325 char *arname, *arpath; 326 Xword ndx; 327 int found, again; 328 int allexrt = (ofl->ofl_flags1 & FLG_OF1_ALLEXRT) != 0; 329 uintptr_t err; 330 Rej_desc rej = { 0 }; 331 332 /* 333 * If a fatal error condition has been set there's really no point in 334 * processing the archive further. Having got to this point we have at 335 * least established that the archive exists (thus verifying that the 336 * command line options that got us to this archive are correct). Very 337 * large archives can take a significant time to process, therefore 338 * continuing on from here may significantly delay the fatal error 339 * message the user is already set to receive. 340 */ 341 if (ofl->ofl_flags & FLG_OF_FATAL) 342 return (1); 343 344 /* 345 * If this archive was processed with -z allextract, then all members 346 * have already been extracted. 347 */ 348 if (adp->ad_elf == NULL) 349 return (1); 350 351 /* 352 * Loop through archive symbol table until we make a complete pass 353 * without satisfying an unresolved reference. For each archive 354 * symbol, see if there is a symbol with the same name in ld's 355 * symbol table. If so, and if that symbol is still unresolved or 356 * tentative, process the corresponding archive member. 357 */ 358 found = again = 0; 359 do { 360 DBG_CALL(Dbg_file_ar(ofl->ofl_lml, name, again)); 361 DBG_CALL(Dbg_syms_ar_title(ofl->ofl_lml, name, again)); 362 363 ndx = again = 0; 364 for (arsym = adp->ad_start, aup = adp->ad_aux; arsym->as_name; 365 ++arsym, ++aup, ndx++) { 366 Rej_desc _rej = { 0 }; 367 Ar_mem *amp; 368 Sym *sym; 369 Boolean visible = TRUE; 370 371 /* 372 * If the auxiliary members value indicates that this 373 * member has been processed then this symbol will have 374 * been added to the output file image already or the 375 * object was rejected in which case we don't want to 376 * process it again. 377 */ 378 if (aup->au_mem == FLG_ARMEM_PROC) 379 continue; 380 381 /* 382 * If the auxiliary symbol element is non-zero lookup 383 * the symbol from the internal symbol table. 384 * (But you skip this if allextract is specified.) 385 */ 386 if ((allexrt == 0) && ((sdp = aup->au_syms) == 0)) { 387 if ((sdp = ld_sym_find(arsym->as_name, 388 /* LINTED */ 389 (Word)arsym->as_hash, 0, ofl)) == 0) { 390 DBG_CALL(Dbg_syms_ar_entry(ofl->ofl_lml, 391 ndx, arsym)); 392 continue; 393 } 394 aup->au_syms = sdp; 395 } 396 397 /* 398 * With '-z allextract', all members will be extracted. 399 * 400 * This archive member is a candidate for extraction if 401 * the internal symbol originates from an explicit file, 402 * and represents an undefined or tentative symbol. 403 * 404 * By default, weak references do not cause archive 405 * extraction, however the -zweakextract flag overrides 406 * this default. 407 * 408 * If this symbol has already been bound to a versioned 409 * shared object, but the shared objects version is not 410 * available, then a definition of this symbol from 411 * within the archive is a better candidate. Similarly, 412 * if this symbol has been bound to a shared object, but 413 * the original reference expected hidden or protected 414 * visibility, then a definition of this symbol from 415 * within the archive is a better candidate. 416 */ 417 if (allexrt == 0) { 418 Boolean vers = TRUE; 419 Ifl_desc *ifl = sdp->sd_file; 420 421 sym = sdp->sd_sym; 422 423 if (sdp->sd_ref == REF_DYN_NEED) { 424 uchar_t vis; 425 426 if (ifl->ifl_vercnt) { 427 Word vndx; 428 Ver_index *vip; 429 430 vndx = sdp->sd_aux->sa_dverndx; 431 vip = &ifl->ifl_verndx[vndx]; 432 if ((vip->vi_flags & 433 FLG_VER_AVAIL) == 0) 434 vers = FALSE; 435 } 436 437 vis = ELF_ST_VISIBILITY(sym->st_other); 438 visible = sym_vis[vis]; 439 } 440 441 if (((ifl->ifl_flags & FLG_IF_NEEDED) == 0) || 442 (visible && vers && 443 (sym->st_shndx != SHN_UNDEF) && 444 (sym->st_shndx != SHN_COMMON)) || 445 ((ELF_ST_BIND(sym->st_info) == STB_WEAK) && 446 (!(ofl->ofl_flags1 & FLG_OF1_WEAKEXT)))) { 447 DBG_CALL(Dbg_syms_ar_entry(ofl->ofl_lml, 448 ndx, arsym)); 449 continue; 450 } 451 } 452 453 /* 454 * Determine if we have already extracted this member, 455 * and if so reuse the Ar_mem information. 456 */ 457 if ((amp = aup->au_mem) != 0) { 458 arelf = amp->am_elf; 459 arname = amp->am_name; 460 arpath = amp->am_path; 461 } else { 462 size_t len; 463 464 /* 465 * Set up a new elf descriptor for this member. 466 */ 467 if (elf_rand(adp->ad_elf, arsym->as_off) != 468 arsym->as_off) { 469 eprintf(ofl->ofl_lml, ERR_ELF, 470 MSG_INTL(MSG_ELF_ARMEM), name, 471 EC_WORD(arsym->as_off), ndx, 472 demangle(arsym->as_name)); 473 ofl->ofl_flags |= FLG_OF_FATAL; 474 return (0); 475 } 476 477 if ((arelf = elf_begin(fd, ELF_C_READ, 478 adp->ad_elf)) == NULL) { 479 eprintf(ofl->ofl_lml, ERR_ELF, 480 MSG_INTL(MSG_ELF_BEGIN), name); 481 ofl->ofl_flags |= FLG_OF_FATAL; 482 return (0); 483 } 484 485 /* 486 * Construct the member filename. 487 */ 488 if ((arhdr = elf_getarhdr(arelf)) == NULL) { 489 eprintf(ofl->ofl_lml, ERR_ELF, 490 MSG_INTL(MSG_ELF_GETARHDR), name); 491 ofl->ofl_flags |= FLG_OF_FATAL; 492 return (0); 493 } 494 arname = arhdr->ar_name; 495 496 /* 497 * Construct the members full pathname, using 498 * the format "%s(%s)". 499 */ 500 len = strlen(name) + strlen(arname) + 3; 501 if ((arpath = libld_malloc(len)) == 0) 502 return (S_ERROR); 503 (void) snprintf(arpath, len, 504 MSG_ORIG(MSG_FMT_ARMEM), name, arname); 505 506 /* 507 * Determine whether the support library wishes 508 * to process this open. See comments in 509 * ld_process_open(). 510 */ 511 ld_sup_open(ofl, (const char **)&arpath, 512 (const char **)&arname, &fd, 513 (FLG_IF_EXTRACT | FLG_IF_NEEDED), 514 &arelf, adp->ad_elf, arsym->as_off, 515 elf_kind(arelf)); 516 517 /* 518 * An ELF descriptor of zero indicates that 519 * the archive member should be ignored. 520 */ 521 if (arelf == NULL) { 522 aup->au_mem = FLG_ARMEM_PROC; 523 continue; 524 } 525 } 526 527 /* 528 * The symbol for which this archive member is being 529 * processed may provide a better alternative to the 530 * symbol that is presently known. Two cases are 531 * covered: 532 * 533 * i. The present symbol represents tentative data. 534 * The archive member may provide a data 535 * definition symbol. 536 * ii. The present symbol represents a reference that 537 * has seen a definition within a shared object 538 * dependency, but the reference expects to be 539 * reduced to hidden or protected visibility. 540 */ 541 if ((allexrt == 0) && 542 ((sym->st_shndx == SHN_COMMON) || 543 (visible == FALSE))) { 544 /* 545 * If we don't already have a member structure 546 * allocate one. 547 */ 548 if (!amp) { 549 if ((amp = libld_calloc(sizeof (Ar_mem), 550 1)) == 0) 551 return (S_ERROR); 552 amp->am_elf = arelf; 553 amp->am_name = arname; 554 amp->am_path = arpath; 555 } 556 DBG_CALL(Dbg_syms_ar_checking(ofl->ofl_lml, 557 ndx, arsym, arname)); 558 if ((err = process_member(amp, arsym->as_name, 559 sdp, ofl)) == S_ERROR) 560 return (S_ERROR); 561 562 /* 563 * If it turns out that we don't need this 564 * member simply initialize all other auxiliary 565 * entries that match this offset with this 566 * members address. In this way we can resuse 567 * this information if we recurse back to this 568 * symbol. 569 */ 570 if (err == 0) { 571 if (aup->au_mem == 0) 572 ld_ar_member(adp, arsym, 573 aup, amp); 574 continue; 575 } 576 } 577 578 /* 579 * Process the archive member. Retain any error for 580 * return to the caller. 581 */ 582 DBG_CALL(Dbg_syms_ar_resolve(ofl->ofl_lml, ndx, arsym, 583 arname, allexrt)); 584 if ((err = (uintptr_t)ld_process_ifl(arpath, NULL, fd, 585 arelf, (FLG_IF_EXTRACT | FLG_IF_NEEDED), ofl, 586 &_rej)) == S_ERROR) 587 return (S_ERROR); 588 589 /* 590 * If this member is rejected maintain the first 591 * rejection error for possible later display. Keep the 592 * member as extracted so that we don't try and process 593 * it again on a rescan. 594 */ 595 if (_rej.rej_type) { 596 if (rej.rej_type == 0) { 597 rej.rej_type = _rej.rej_type; 598 rej.rej_info = _rej.rej_info; 599 rej.rej_name = (const char *)arpath; 600 } 601 ld_ar_member(adp, arsym, aup, FLG_ARMEM_PROC); 602 continue; 603 } 604 605 /* 606 * Indicate that the extracted member is in use. This 607 * enables debugging diags, and indicates that a further 608 * rescan of all archives may be necessary. 609 */ 610 found = 1; 611 ofl->ofl_flags1 |= FLG_OF1_EXTRACT; 612 adp->ad_flags |= FLG_ARD_EXTRACT; 613 614 /* 615 * If not under '-z allextract' signal the need to 616 * rescan this archive. 617 */ 618 if (allexrt == 0) 619 again = 1; 620 621 ld_ar_member(adp, arsym, aup, FLG_ARMEM_PROC); 622 DBG_CALL(Dbg_util_nl(ofl->ofl_lml, DBG_NL_STD)); 623 } 624 } while (again); 625 626 /* 627 * If no objects have been found in the archive test for any rejections 628 * and if one had occurred issue a warning - its possible a user has 629 * pointed at an archive containing the wrong class of elf members. 630 */ 631 if ((found == 0) && rej.rej_type) { 632 Conv_reject_desc_buf_t rej_buf; 633 634 eprintf(ofl->ofl_lml, ERR_WARNING, 635 MSG_INTL(reject[rej.rej_type]), 636 rej.rej_name ? rej.rej_name : MSG_INTL(MSG_STR_UNKNOWN), 637 conv_reject_desc(&rej, &rej_buf, ld_targ.t_m.m_mach)); 638 } 639 640 /* 641 * If this archive was extracted by -z allextract, the ar_aux table 642 * and elf descriptor can be freed. Set ad_elf to NULL to mark the 643 * archive is completely processed. 644 */ 645 if (allexrt) { 646 (void) elf_end(adp->ad_elf); 647 adp->ad_elf = NULL; 648 } 649 650 return (1); 651 } 652