aboutsummaryrefslogtreecommitdiff
path: root/elf
diff options
context:
space:
mode:
Diffstat (limited to 'elf')
-rw-r--r--elf/Makefile1412
-rw-r--r--elf/Versions77
-rw-r--r--elf/cache.c829
-rw-r--r--elf/chroot_canon.c177
-rw-r--r--elf/circleload1.c166
-rw-r--r--elf/circlemod1.c7
-rw-r--r--elf/circlemod1a.c1
-rw-r--r--elf/circlemod2.c9
-rw-r--r--elf/circlemod2a.c7
-rw-r--r--elf/circlemod3.c14
-rw-r--r--elf/circlemod3a.c1
-rw-r--r--elf/constload1.c32
-rw-r--r--elf/constload2.c50
-rw-r--r--elf/constload3.c8
-rw-r--r--elf/dblload.c53
-rw-r--r--elf/dblloadmod1.c8
-rw-r--r--elf/dblloadmod2.c15
-rw-r--r--elf/dblloadmod3.c8
-rw-r--r--elf/dblunload.c53
-rw-r--r--elf/dep1.c25
-rw-r--r--elf/dep2.c25
-rw-r--r--elf/dep3.c23
-rw-r--r--elf/dep4.c24
-rw-r--r--elf/dl-addr-obj.c75
-rw-r--r--elf/dl-addr.c146
-rw-r--r--elf/dl-brk.c5
-rw-r--r--elf/dl-cache.c325
-rw-r--r--elf/dl-caller.c86
-rw-r--r--elf/dl-close.c843
-rw-r--r--elf/dl-conflict.c74
-rw-r--r--elf/dl-debug.c76
-rw-r--r--elf/dl-deps.c688
-rw-r--r--elf/dl-dst.h74
-rw-r--r--elf/dl-environ.c85
-rw-r--r--elf/dl-error-minimal.c23
-rw-r--r--elf/dl-error-skeleton.c230
-rw-r--r--elf/dl-error.c27
-rw-r--r--elf/dl-execstack.c31
-rw-r--r--elf/dl-fini.c281
-rw-r--r--elf/dl-fptr.c322
-rw-r--r--elf/dl-hwcaps.c297
-rw-r--r--elf/dl-hwcaps.h30
-rw-r--r--elf/dl-init.c126
-rw-r--r--elf/dl-iteratephdr.c89
-rw-r--r--elf/dl-libc.c330
-rw-r--r--elf/dl-load.c2307
-rw-r--r--elf/dl-load.h135
-rw-r--r--elf/dl-lookup.c1129
-rw-r--r--elf/dl-machine-reject-phdr.h34
-rw-r--r--elf/dl-map-segments.h157
-rw-r--r--elf/dl-minimal.c380
-rw-r--r--elf/dl-misc.c362
-rw-r--r--elf/dl-object.c229
-rw-r--r--elf/dl-open.c737
-rw-r--r--elf/dl-origin.c50
-rw-r--r--elf/dl-profile.c596
-rw-r--r--elf/dl-profstub.c41
-rw-r--r--elf/dl-reloc.c363
-rw-r--r--elf/dl-runtime.c480
-rw-r--r--elf/dl-sbrk.c5
-rw-r--r--elf/dl-scope.c57
-rw-r--r--elf/dl-support.c389
-rw-r--r--elf/dl-sym.c274
-rw-r--r--elf/dl-symaddr.c33
-rw-r--r--elf/dl-sysdep-open.h45
-rw-r--r--elf/dl-sysdep.c360
-rw-r--r--elf/dl-tls.c953
-rw-r--r--elf/dl-trampoline.c1
-rw-r--r--elf/dl-tunable-types.h62
-rw-r--r--elf/dl-tunables.c490
-rw-r--r--elf/dl-tunables.h115
-rw-r--r--elf/dl-tunables.list87
-rw-r--r--elf/dl-unmap-segments.h35
-rw-r--r--elf/dl-version.c389
-rw-r--r--elf/dl-writev.h56
-rw-r--r--elf/do-rel.h191
-rw-r--r--elf/dynamic-link.h203
-rw-r--r--elf/elf.h3761
-rw-r--r--elf/enbl-secure.c36
-rw-r--r--elf/failobj.c10
-rw-r--r--elf/filter.c19
-rw-r--r--elf/filtmod1.c7
-rw-r--r--elf/filtmod2.c7
-rw-r--r--elf/firstobj.c10
-rw-r--r--elf/gen-trusted-dirs.awk37
-rw-r--r--elf/genrtldtbl.awk29
-rw-r--r--elf/get-dynamic-info.h184
-rw-r--r--elf/global.c7
-rw-r--r--elf/globalmod1.c17
-rw-r--r--elf/ifuncdep1.c3
-rw-r--r--elf/ifuncdep1pic.c3
-rw-r--r--elf/ifuncdep2.c59
-rw-r--r--elf/ifuncdep2pic.c3
-rw-r--r--elf/ifuncdep5.c3
-rw-r--r--elf/ifuncdep5pic.c3
-rw-r--r--elf/ifuncmain1.c64
-rw-r--r--elf/ifuncmain1pic.c3
-rw-r--r--elf/ifuncmain1picstatic.c3
-rw-r--r--elf/ifuncmain1pie.c3
-rw-r--r--elf/ifuncmain1static.c3
-rw-r--r--elf/ifuncmain1staticpic.c3
-rw-r--r--elf/ifuncmain1staticpie.c3
-rw-r--r--elf/ifuncmain1vis.c87
-rw-r--r--elf/ifuncmain1vispic.c3
-rw-r--r--elf/ifuncmain1vispie.c3
-rw-r--r--elf/ifuncmain2.c14
-rw-r--r--elf/ifuncmain2pic.c3
-rw-r--r--elf/ifuncmain2picstatic.c3
-rw-r--r--elf/ifuncmain2static.c3
-rw-r--r--elf/ifuncmain3.c129
-rw-r--r--elf/ifuncmain4.c4
-rw-r--r--elf/ifuncmain4picstatic.c3
-rw-r--r--elf/ifuncmain4static.c3
-rw-r--r--elf/ifuncmain5.c38
-rw-r--r--elf/ifuncmain5pic.c3
-rw-r--r--elf/ifuncmain5picstatic.c3
-rw-r--r--elf/ifuncmain5pie.c3
-rw-r--r--elf/ifuncmain5static.c3
-rw-r--r--elf/ifuncmain5staticpic.c3
-rw-r--r--elf/ifuncmain6pie.c65
-rw-r--r--elf/ifuncmain7.c72
-rw-r--r--elf/ifuncmain7pic.c7
-rw-r--r--elf/ifuncmain7picstatic.c7
-rw-r--r--elf/ifuncmain7pie.c7
-rw-r--r--elf/ifuncmain7static.c7
-rw-r--r--elf/ifuncmod1.c100
-rw-r--r--elf/ifuncmod3.c7
-rw-r--r--elf/ifuncmod5.c64
-rw-r--r--elf/ifuncmod6.c19
-rw-r--r--elf/initfirst.c22
-rw-r--r--elf/interp.c22
-rw-r--r--elf/lateglobal.c47
-rw-r--r--elf/ldconfig.c1418
-rw-r--r--elf/ldd.bash.in203
-rw-r--r--elf/link.h194
-rw-r--r--elf/loadfail.c42
-rw-r--r--elf/loadtest.c202
-rw-r--r--elf/ltglobmod1.c7
-rw-r--r--elf/ltglobmod2.c33
-rw-r--r--elf/multiload.c105
-rw-r--r--elf/neededobj1.c6
-rw-r--r--elf/neededobj2.c8
-rw-r--r--elf/neededobj3.c10
-rw-r--r--elf/neededobj4.c12
-rw-r--r--elf/neededobj5.c5
-rw-r--r--elf/neededobj6.c7
-rw-r--r--elf/neededtest.c125
-rw-r--r--elf/neededtest2.c118
-rw-r--r--elf/neededtest3.c129
-rw-r--r--elf/neededtest4.c158
-rw-r--r--elf/next.c43
-rw-r--r--elf/nextmod1.c30
-rw-r--r--elf/nextmod2.c10
-rw-r--r--elf/nodel2mod1.c19
-rw-r--r--elf/nodel2mod2.c7
-rw-r--r--elf/nodel2mod3.c1
-rw-r--r--elf/nodelete.c210
-rw-r--r--elf/nodelete2.c16
-rw-r--r--elf/nodelmod1.c9
-rw-r--r--elf/nodelmod2.c9
-rw-r--r--elf/nodelmod3.c8
-rw-r--r--elf/nodelmod4.c9
-rw-r--r--elf/nodlopen.c15
-rw-r--r--elf/nodlopen2.c15
-rw-r--r--elf/nodlopenmod.c1
-rw-r--r--elf/nodlopenmod2.c9
-rw-r--r--elf/noload.c81
-rw-r--r--elf/order.c25
-rw-r--r--elf/order2.c45
-rw-r--r--elf/order2mod1.c8
-rw-r--r--elf/order2mod2.c18
-rw-r--r--elf/order2mod3.c14
-rw-r--r--elf/order2mod4.c16
-rw-r--r--elf/origtest.c39
-rw-r--r--elf/pathoptobj.c8
-rw-r--r--elf/pldd-xx.c251
-rw-r--r--elf/pldd.c344
-rw-r--r--elf/preloadtest.c19
-rw-r--r--elf/readelflib.c234
-rw-r--r--elf/readlib.c212
-rw-r--r--elf/reldep.c111
-rw-r--r--elf/reldep2.c101
-rw-r--r--elf/reldep3.c101
-rw-r--r--elf/reldep4.c40
-rw-r--r--elf/reldep4mod1.c7
-rw-r--r--elf/reldep4mod2.c8
-rw-r--r--elf/reldep4mod3.c7
-rw-r--r--elf/reldep4mod4.c8
-rw-r--r--elf/reldep5.c70
-rw-r--r--elf/reldep6.c109
-rw-r--r--elf/reldep6mod0.c8
-rw-r--r--elf/reldep6mod1.c14
-rw-r--r--elf/reldep6mod2.c3
-rw-r--r--elf/reldep6mod3.c3
-rw-r--r--elf/reldep6mod4.c12
-rw-r--r--elf/reldep7.c58
-rw-r--r--elf/reldep7mod1.c12
-rw-r--r--elf/reldep7mod2.c12
-rw-r--r--elf/reldep8.c16
-rw-r--r--elf/reldep8mod1.c19
-rw-r--r--elf/reldep8mod2.c7
-rw-r--r--elf/reldep8mod3.c1
-rw-r--r--elf/reldep9.c16
-rw-r--r--elf/reldep9mod1.c23
-rw-r--r--elf/reldep9mod2.c3
-rw-r--r--elf/reldep9mod3.c1
-rw-r--r--elf/reldepmod1.c10
-rw-r--r--elf/reldepmod2.c8
-rw-r--r--elf/reldepmod3.c20
-rw-r--r--elf/reldepmod4.c37
-rw-r--r--elf/reldepmod5.c7
-rw-r--r--elf/reldepmod6.c8
-rw-r--r--elf/resolvfail.c31
-rw-r--r--elf/restest1.c57
-rw-r--r--elf/restest2.c33
-rw-r--r--elf/rtld-Rules149
-rw-r--r--elf/rtld-debugger-interface.txt122
-rw-r--r--elf/rtld.c2652
-rw-r--r--elf/setup-vdso.h121
-rw-r--r--elf/sln.c202
-rw-r--r--elf/sofini.c19
-rw-r--r--elf/soinit.c43
-rw-r--r--elf/sotruss-lib.c386
-rwxr-xr-xelf/sotruss.sh152
-rw-r--r--elf/sprof.c1436
-rw-r--r--elf/static-stubs.c46
-rw-r--r--elf/testobj.h28
-rw-r--r--elf/testobj1.c25
-rw-r--r--elf/testobj1_1.c7
-rw-r--r--elf/testobj2.c32
-rw-r--r--elf/testobj3.c26
-rw-r--r--elf/testobj4.c25
-rw-r--r--elf/testobj5.c26
-rw-r--r--elf/testobj6.c19
-rw-r--r--elf/tls-macros.h25
-rw-r--r--elf/tlsdeschtab.h164
-rw-r--r--elf/tst-_dl_addr_inside_object.c222
-rw-r--r--elf/tst-addr1.c25
-rw-r--r--elf/tst-align.c52
-rw-r--r--elf/tst-align2.c155
-rw-r--r--elf/tst-alignmod.c52
-rw-r--r--elf/tst-alignmod2.c59
-rw-r--r--elf/tst-array1-static.c1
-rw-r--r--elf/tst-array1.c103
-rw-r--r--elf/tst-array1.exp11
-rw-r--r--elf/tst-array2.c1
-rw-r--r--elf/tst-array2.exp19
-rw-r--r--elf/tst-array2dep.c71
-rw-r--r--elf/tst-array3.c1
-rw-r--r--elf/tst-array4.c18
-rw-r--r--elf/tst-array4.exp19
-rw-r--r--elf/tst-array5-static.c1
-rw-r--r--elf/tst-array5-static.exp2
-rw-r--r--elf/tst-array5.c50
-rw-r--r--elf/tst-array5.exp3
-rw-r--r--elf/tst-array5dep.c23
-rw-r--r--elf/tst-audit1.c1
-rw-r--r--elf/tst-audit11.c35
-rw-r--r--elf/tst-audit11mod1.c24
-rw-r--r--elf/tst-audit11mod2.c23
-rw-r--r--elf/tst-audit11mod2.map22
-rw-r--r--elf/tst-audit12.c48
-rw-r--r--elf/tst-audit12mod1.c24
-rw-r--r--elf/tst-audit12mod2.c23
-rw-r--r--elf/tst-audit12mod2.map22
-rw-r--r--elf/tst-audit12mod3.c23
-rw-r--r--elf/tst-audit2.c60
-rw-r--r--elf/tst-audit8.c1
-rw-r--r--elf/tst-audit9.c11
-rw-r--r--elf/tst-auditmod1.c135
-rw-r--r--elf/tst-auditmod11.c39
-rw-r--r--elf/tst-auditmod12.c43
-rw-r--r--elf/tst-auditmod9a.c15
-rw-r--r--elf/tst-auditmod9b.c6
-rw-r--r--elf/tst-auxv.c70
-rw-r--r--elf/tst-deep1.c35
-rw-r--r--elf/tst-deep1mod1.c14
-rw-r--r--elf/tst-deep1mod2.c16
-rw-r--r--elf/tst-deep1mod3.c17
-rw-r--r--elf/tst-dl-iter-static.c46
-rw-r--r--elf/tst-dlmodcount.c108
-rw-r--r--elf/tst-dlmopen1.c80
-rw-r--r--elf/tst-dlmopen1mod.c59
-rw-r--r--elf/tst-dlmopen2.c69
-rw-r--r--elf/tst-dlmopen3.c21
-rw-r--r--elf/tst-dlopen-aout.c67
-rw-r--r--elf/tst-dlopenrpath.c70
-rw-r--r--elf/tst-dlopenrpathmod.c35
-rw-r--r--elf/tst-dlsym-error.c113
-rw-r--r--elf/tst-env-setuid-tunables.c75
-rw-r--r--elf/tst-env-setuid.c296
-rw-r--r--elf/tst-execstack-mod.c30
-rw-r--r--elf/tst-execstack-needed.c34
-rw-r--r--elf/tst-execstack-prog.c33
-rw-r--r--elf/tst-execstack.c236
-rw-r--r--elf/tst-global1.c38
-rw-r--r--elf/tst-gnu2-tls1.c51
-rw-r--r--elf/tst-gnu2-tls1mod.c56
-rw-r--r--elf/tst-initorder.c7
-rw-r--r--elf/tst-initorder.exp13
-rw-r--r--elf/tst-initorder2.c20
-rw-r--r--elf/tst-initorder2.exp9
-rw-r--r--elf/tst-initordera1.c16
-rw-r--r--elf/tst-initordera2.c16
-rw-r--r--elf/tst-initordera3.c16
-rw-r--r--elf/tst-initordera4.c16
-rw-r--r--elf/tst-initorderb1.c16
-rw-r--r--elf/tst-initorderb2.c16
-rw-r--r--elf/tst-latepthread.c104
-rw-r--r--elf/tst-latepthreadmod.c33
-rw-r--r--elf/tst-ldconfig-X.sh62
-rw-r--r--elf/tst-leaks1-static.c1
-rw-r--r--elf/tst-leaks1.c27
-rw-r--r--elf/tst-linkall-static.c52
-rw-r--r--elf/tst-nodelete-dlclose-dso.c90
-rw-r--r--elf/tst-nodelete-dlclose-plugin.c40
-rw-r--r--elf/tst-nodelete-dlclose.c35
-rw-r--r--elf/tst-nodelete-opened-lib.c19
-rw-r--r--elf/tst-nodelete-opened.c68
-rw-r--r--elf/tst-nodelete-rtldmod.cc6
-rw-r--r--elf/tst-nodelete-uniquemod.cc14
-rw-r--r--elf/tst-nodelete-zmod.cc6
-rw-r--r--elf/tst-nodelete.cc50
-rw-r--r--elf/tst-nodelete2.c36
-rw-r--r--elf/tst-nodelete2mod.c7
-rw-r--r--elf/tst-noload.c72
-rw-r--r--elf/tst-null-argv-lib.c24
-rw-r--r--elf/tst-null-argv.c36
-rw-r--r--elf/tst-order-a1.c16
-rw-r--r--elf/tst-order-a2.c16
-rw-r--r--elf/tst-order-a3.c16
-rw-r--r--elf/tst-order-a4.c16
-rw-r--r--elf/tst-order-b1.c16
-rw-r--r--elf/tst-order-b2.c16
-rw-r--r--elf/tst-order-main.c12
-rw-r--r--elf/tst-pathopt.c41
-rwxr-xr-xelf/tst-pathopt.sh39
-rw-r--r--elf/tst-pie1.c5
-rw-r--r--elf/tst-pie2.c40
-rw-r--r--elf/tst-piemod1.c22
-rw-r--r--elf/tst-prelink.c29
-rw-r--r--elf/tst-prelink.exp1
-rw-r--r--elf/tst-protected1a.c234
-rw-r--r--elf/tst-protected1b.c240
-rw-r--r--elf/tst-protected1mod.h41
-rw-r--r--elf/tst-protected1moda.c92
-rw-r--r--elf/tst-protected1modb.c62
-rw-r--r--elf/tst-ptrguard1-static.c1
-rw-r--r--elf/tst-ptrguard1.c217
-rw-r--r--elf/tst-relsort1.c18
-rw-r--r--elf/tst-relsort1mod1.c7
-rw-r--r--elf/tst-relsort1mod2.c7
-rwxr-xr-xelf/tst-rtld-load-self.sh49
-rw-r--r--elf/tst-stackguard1-static.c1
-rw-r--r--elf/tst-stackguard1.c205
-rw-r--r--elf/tst-thrlock.c58
-rw-r--r--elf/tst-tls-dlinfo.c85
-rw-r--r--elf/tst-tls-manydynamic.c151
-rw-r--r--elf/tst-tls-manydynamic.h44
-rw-r--r--elf/tst-tls-manydynamicmod.c36
-rw-r--r--elf/tst-tls1-static.c1
-rw-r--r--elf/tst-tls1.c82
-rw-r--r--elf/tst-tls10.c39
-rw-r--r--elf/tst-tls10.h32
-rw-r--r--elf/tst-tls11.c28
-rw-r--r--elf/tst-tls12.c19
-rw-r--r--elf/tst-tls13.c28
-rw-r--r--elf/tst-tls14.c54
-rw-r--r--elf/tst-tls15.c32
-rw-r--r--elf/tst-tls16.c52
-rw-r--r--elf/tst-tls17.c28
-rw-r--r--elf/tst-tls18.c37
-rw-r--r--elf/tst-tls19.c26
-rw-r--r--elf/tst-tls19mod1.c15
-rw-r--r--elf/tst-tls19mod2.c13
-rw-r--r--elf/tst-tls19mod3.c16
-rw-r--r--elf/tst-tls2-static.c1
-rw-r--r--elf/tst-tls2.c82
-rw-r--r--elf/tst-tls3.c67
-rw-r--r--elf/tst-tls4.c49
-rw-r--r--elf/tst-tls5.c65
-rw-r--r--elf/tst-tls6.c84
-rw-r--r--elf/tst-tls7.c55
-rw-r--r--elf/tst-tls8.c167
-rw-r--r--elf/tst-tls9-static.c1
-rw-r--r--elf/tst-tls9.c36
-rw-r--r--elf/tst-tlsalign-extern-static.c1
-rw-r--r--elf/tst-tlsalign-extern.c73
-rw-r--r--elf/tst-tlsalign-lib.c6
-rw-r--r--elf/tst-tlsalign-static.c2
-rw-r--r--elf/tst-tlsalign-vars.c28
-rw-r--r--elf/tst-tlsalign.c84
-rw-r--r--elf/tst-tlsmod1.c62
-rw-r--r--elf/tst-tlsmod10.c1
-rw-r--r--elf/tst-tlsmod11.c4
-rw-r--r--elf/tst-tlsmod12.c12
-rw-r--r--elf/tst-tlsmod13.c7
-rw-r--r--elf/tst-tlsmod13a.c9
-rw-r--r--elf/tst-tlsmod14a.c35
-rw-r--r--elf/tst-tlsmod14b.c2
-rw-r--r--elf/tst-tlsmod15a.c6
-rw-r--r--elf/tst-tlsmod15b.c9
-rw-r--r--elf/tst-tlsmod16a.c1
-rw-r--r--elf/tst-tlsmod16b.c7
-rw-r--r--elf/tst-tlsmod17a.c23
-rw-r--r--elf/tst-tlsmod17b.c15
-rw-r--r--elf/tst-tlsmod18a.c21
-rw-r--r--elf/tst-tlsmod2.c34
-rw-r--r--elf/tst-tlsmod3.c37
-rw-r--r--elf/tst-tlsmod4.c34
-rw-r--r--elf/tst-tlsmod5.c3
-rw-r--r--elf/tst-tlsmod6.c3
-rw-r--r--elf/tst-tlsmod7.c101
-rw-r--r--elf/tst-tlsmod8.c70
-rw-r--r--elf/tst-tlsmod9.c99
-rw-r--r--elf/tst-unique1.c73
-rw-r--r--elf/tst-unique1mod1.c16
-rw-r--r--elf/tst-unique1mod2.c15
-rw-r--r--elf/tst-unique2.c27
-rw-r--r--elf/tst-unique2mod1.c8
-rw-r--r--elf/tst-unique2mod2.c15
-rw-r--r--elf/tst-unique3.cc24
-rw-r--r--elf/tst-unique3.h8
-rw-r--r--elf/tst-unique3lib.cc11
-rw-r--r--elf/tst-unique3lib2.cc12
-rw-r--r--elf/tst-unique4.cc28
-rw-r--r--elf/tst-unique4.h7
-rw-r--r--elf/tst-unique4lib.cc17
-rw-r--r--elf/unload.c91
-rw-r--r--elf/unload2.c59
-rw-r--r--elf/unload2dep.c6
-rw-r--r--elf/unload2mod.c8
-rw-r--r--elf/unload3.c41
-rw-r--r--elf/unload3mod1.c1
-rw-r--r--elf/unload3mod2.c1
-rw-r--r--elf/unload3mod3.c8
-rw-r--r--elf/unload3mod4.c13
-rw-r--r--elf/unload4.c48
-rw-r--r--elf/unload4mod1.c10
-rw-r--r--elf/unload4mod2.c8
-rw-r--r--elf/unload4mod3.c16
-rw-r--r--elf/unload4mod4.c16
-rw-r--r--elf/unload5.c42
-rw-r--r--elf/unload6.c30
-rw-r--r--elf/unload6mod1.c16
-rw-r--r--elf/unload6mod2.c23
-rw-r--r--elf/unload6mod3.c23
-rw-r--r--elf/unload7.c39
-rw-r--r--elf/unload7mod1.c11
-rw-r--r--elf/unload7mod2.c1
-rw-r--r--elf/unload8.c33
-rw-r--r--elf/unload8mod1.c7
-rw-r--r--elf/unload8mod1x.c1
-rw-r--r--elf/unload8mod2.c7
-rw-r--r--elf/unload8mod3.c27
-rw-r--r--elf/unloadmod.c4
-rw-r--r--elf/vismain.c260
-rw-r--r--elf/vismod.h27
-rw-r--r--elf/vismod1.c103
-rw-r--r--elf/vismod2.c123
-rw-r--r--elf/vismod3.c46
461 files changed, 0 insertions, 43439 deletions
diff --git a/elf/Makefile b/elf/Makefile
deleted file mode 100644
index 201b328f88..0000000000
--- a/elf/Makefile
+++ /dev/null
@@ -1,1412 +0,0 @@
-# Copyright (C) 1995-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-# Makefile for elf subdirectory of GNU C Library.
-
-subdir := elf
-
-include ../Makeconfig
-
-headers = elf.h bits/elfclass.h link.h bits/link.h
-routines = $(all-dl-routines) dl-support dl-iteratephdr \
- dl-addr dl-addr-obj enbl-secure dl-profstub \
- dl-origin dl-libc dl-sym dl-sysdep dl-error
-
-# The core dynamic linking functions are in libc for the static and
-# profiled libraries.
-dl-routines = $(addprefix dl-,load lookup object reloc deps hwcaps \
- runtime init fini debug misc \
- version profile conflict tls origin scope \
- execstack caller open close trampoline)
-ifeq (yes,$(use-ldconfig))
-dl-routines += dl-cache
-endif
-
-ifneq (no,$(have-tunables))
-dl-routines += dl-tunables
-tunables-type = $(addprefix TUNABLES_FRONTEND_,$(have-tunables))
-CPPFLAGS-dl-tunables.c = -DTUNABLES_FRONTEND=$(tunables-type)
-
-# Make sure that the compiler does not insert any library calls in tunables
-# code paths.
-ifeq (yes,$(have-loop-to-function))
-CFLAGS-dl-tunables.c = -fno-tree-loop-distribute-patterns
-endif
-endif
-
-all-dl-routines = $(dl-routines) $(sysdep-dl-routines)
-# But they are absent from the shared libc, because that code is in ld.so.
-elide-routines.os = $(all-dl-routines) dl-support enbl-secure dl-origin \
- dl-sysdep
-shared-only-routines += dl-caller
-
-# ld.so uses those routines, plus some special stuff for being the program
-# interpreter and operating independent of libc.
-rtld-routines = rtld $(all-dl-routines) dl-sysdep dl-environ dl-minimal \
- dl-error-minimal
-all-rtld-routines = $(rtld-routines) $(sysdep-rtld-routines)
-
-CFLAGS-dl-runtime.c = -fexceptions -fasynchronous-unwind-tables
-CFLAGS-dl-lookup.c = -fexceptions -fasynchronous-unwind-tables
-CFLAGS-dl-iterate-phdr.c = $(uses-callbacks)
-
-# Compile rtld itself without stack protection.
-# Also compile all routines in the static library that are elided from
-# the shared libc because they are in libc.a in the same way.
-
-define elide-stack-protector
-$(if $(filter $(@F),$(patsubst %,%$(1),$(2))), $(no-stack-protector))
-endef
-
-CFLAGS-.o += $(call elide-stack-protector,.o,$(elide-routines.os))
-CFLAGS-.op += $(call elide-stack-protector,.op,$(elide-routines.os))
-CFLAGS-.os += $(call elide-stack-protector,.os,$(all-rtld-routines))
-
-ifeq ($(unwind-find-fde),yes)
-routines += unwind-dw2-fde-glibc
-shared-only-routines += unwind-dw2-fde-glibc
-endif
-
-before-compile += $(objpfx)trusted-dirs.h
-generated += trusted-dirs.h trusted-dirs.st for-renamed/renamed.so
-generated-dirs += for-renamed
-
-ifeq ($(build-shared),yes)
-ld-map = $(common-objpfx)ld.map
-endif
-
-ifeq (yes,$(build-shared))
-extra-objs = $(all-rtld-routines:%=%.os) soinit.os sofini.os interp.os
-generated += librtld.os dl-allobjs.os ld.so ldd
-install-others = $(inst_rtlddir)/$(rtld-installed-name)
-install-bin-script = ldd
-endif
-
-others = sprof sln
-install-bin = sprof
-others-static = sln
-install-rootsbin = sln
-sln-modules := static-stubs
-extra-objs += $(sln-modules:=.o)
-
-ifeq (yes,$(use-ldconfig))
-ifeq (yes,$(build-shared))
-others-static += ldconfig
-others += ldconfig
-install-rootsbin += ldconfig
-
-ldconfig-modules := cache readlib xmalloc xstrdup chroot_canon static-stubs
-extra-objs += $(ldconfig-modules:=.o)
-endif
-endif
-
-# To find xmalloc.c and xstrdup.c
-vpath %.c ../locale/programs
-
-ifeq ($(build-shared),yes)
-extra-objs += sotruss-lib.os sotruss-lib.so
-install-others += $(inst_auditdir)/sotruss-lib.so
-install-bin-script += sotruss
-generated += sotruss
-libof-sotruss-lib = extramodules
-$(objpfx)sotruss-lib.so: $(objpfx)sotruss-lib.os
- $(build-module-asneeded)
-$(objpfx)sotruss-lib.so: $(common-objpfx)libc.so $(objpfx)ld.so \
- $(common-objpfx)libc_nonshared.a
-
-$(objpfx)sotruss: sotruss.sh $(common-objpfx)config.make
- sed -e 's%@BASH@%$(BASH)%g' \
- -e 's%@VERSION@%$(version)%g' \
- -e 's%@TEXTDOMAINDIR@%$(localedir)%g' \
- -e 's%@PREFIX@%$(prefix)%g' \
- -e 's|@PKGVERSION@|$(PKGVERSION)|g' \
- -e 's|@REPORT_BUGS_TO@|$(REPORT_BUGS_TO)|g' \
- < $< > $@.new
- chmod 555 $@.new
- mv -f $@.new $@
-$(inst_auditdir)/sotruss-lib.so: $(objpfx)sotruss-lib.so $(+force)
- $(do-install-program)
-endif
-
-tests-static-normal := tst-leaks1-static tst-array1-static tst-array5-static \
- tst-dl-iter-static \
- tst-tlsalign-static tst-tlsalign-extern-static \
- tst-linkall-static tst-env-setuid tst-env-setuid-tunables
-tests-static-internal := tst-tls1-static tst-tls2-static \
- tst-ptrguard1-static tst-stackguard1-static
-
-tests := tst-tls9 tst-leaks1 \
- tst-array1 tst-array2 tst-array3 tst-array4 tst-array5 \
- tst-auxv
-tests-internal := tst-tls1 tst-tls2 $(tests-static-internal)
-tests-static := $(tests-static-normal) $(tests-static-internal)
-
-ifeq (yes,$(build-shared))
-tests-static += tst-tls9-static
-tst-tls9-static-ENV = \
- LD_LIBRARY_PATH=$(objpfx):$(common-objpfx):$(common-objpfx)dlfcn
-
-tests += restest1 preloadtest loadfail multiload origtest resolvfail \
- constload1 order noload filter \
- reldep reldep2 reldep3 reldep4 nodelete nodelete2 \
- nodlopen nodlopen2 lateglobal initfirst global \
- restest2 next dblload dblunload reldep5 reldep6 reldep7 reldep8 \
- tst-tls4 tst-tls5 \
- tst-tls10 tst-tls11 tst-tls12 tst-tls13 tst-tls14 tst-tls15 \
- tst-tls16 tst-tls17 tst-tls18 tst-tls19 tst-tls-dlinfo \
- tst-align tst-align2 $(tests-execstack-$(have-z-execstack)) \
- tst-dlmodcount tst-dlopenrpath tst-deep1 \
- tst-dlmopen1 tst-dlmopen3 \
- unload3 unload4 unload5 unload6 unload7 unload8 tst-global1 order2 \
- tst-audit1 tst-audit2 tst-audit8 tst-audit9 \
- tst-addr1 tst-thrlock \
- tst-unique1 tst-unique2 $(if $(CXX),tst-unique3 tst-unique4 \
- tst-nodelete) \
- tst-initorder tst-initorder2 tst-relsort1 tst-null-argv \
- tst-tlsalign tst-tlsalign-extern tst-nodelete-opened \
- tst-nodelete2 tst-audit11 tst-audit12 tst-dlsym-error tst-noload \
- tst-latepthread tst-tls-manydynamic tst-nodelete-dlclose
-# reldep9
-tests-internal += loadtest unload unload2 circleload1 \
- neededtest neededtest2 neededtest3 neededtest4 \
- tst-tls3 tst-tls6 tst-tls7 tst-tls8 tst-dlmopen2 \
- tst-ptrguard1 tst-stackguard1
-ifeq ($(build-hardcoded-path-in-tests),yes)
-tests += tst-dlopen-aout
-LDFLAGS-tst-dlopen-aout = $(no-pie-ldflag)
-endif
-test-srcs = tst-pathopt
-selinux-enabled := $(shell cat /selinux/enforce 2> /dev/null)
-ifneq ($(selinux-enabled),1)
-tests-execstack-yes = tst-execstack tst-execstack-needed tst-execstack-prog
-endif
-endif
-ifeq ($(run-built-tests),yes)
-tests-special += $(objpfx)tst-leaks1-mem.out \
- $(objpfx)tst-leaks1-static-mem.out $(objpfx)noload-mem.out \
- $(objpfx)tst-ldconfig-X.out
-endif
-tlsmod17a-suffixes = 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
-tlsmod18a-suffixes = 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
-tlsmod17a-modules = $(addprefix tst-tlsmod17a, $(tlsmod17a-suffixes))
-tlsmod18a-modules = $(addprefix tst-tlsmod18a, $(tlsmod17a-suffixes))
-one-hundred = $(foreach x,0 1 2 3 4 5 6 7 8 9, \
- 0$x 1$x 2$x 3$x 4$x 5$x 6$x 7$x 8$x 9$x)
-tst-tls-many-dynamic-modules := \
- $(foreach n,$(one-hundred),tst-tls-manydynamic$(n)mod)
-extra-test-objs += $(tlsmod17a-modules:=.os) $(tlsmod18a-modules:=.os) \
- tst-tlsalign-vars.o
-test-extras += tst-tlsmod17a tst-tlsmod18a tst-tlsalign-vars
-modules-names = testobj1 testobj2 testobj3 testobj4 testobj5 testobj6 \
- testobj1_1 failobj constload2 constload3 unloadmod \
- dep1 dep2 dep3 dep4 vismod1 vismod2 vismod3 \
- nodelmod1 nodelmod2 nodelmod3 nodelmod4 \
- nodel2mod1 nodel2mod2 nodel2mod3 \
- nodlopenmod nodlopenmod2 filtmod1 filtmod2 \
- reldepmod1 reldepmod2 reldepmod3 reldepmod4 nextmod1 nextmod2 \
- reldep4mod1 reldep4mod2 reldep4mod3 reldep4mod4 \
- neededobj1 neededobj2 neededobj3 neededobj4 \
- neededobj5 neededobj6 firstobj globalmod1 \
- unload2mod unload2dep ltglobmod1 ltglobmod2 pathoptobj \
- dblloadmod1 dblloadmod2 dblloadmod3 reldepmod5 reldepmod6 \
- reldep6mod0 reldep6mod1 reldep6mod2 reldep6mod3 reldep6mod4 \
- reldep7mod1 reldep7mod2 \
- tst-tlsmod1 tst-tlsmod2 tst-tlsmod3 tst-tlsmod4 \
- tst-tlsmod5 tst-tlsmod6 tst-tlsmod7 tst-tlsmod8 \
- tst-tlsmod9 tst-tlsmod10 tst-tlsmod11 tst-tlsmod12 \
- tst-tlsmod13 tst-tlsmod13a tst-tlsmod14a tst-tlsmod14b \
- tst-tlsmod15a tst-tlsmod15b tst-tlsmod16a tst-tlsmod16b \
- $(tlsmod17a-modules) tst-tlsmod17b $(tlsmod18a-modules) \
- tst-tls19mod1 tst-tls19mod2 tst-tls19mod3 \
- circlemod1 circlemod1a circlemod2 circlemod2a \
- circlemod3 circlemod3a \
- reldep8mod1 reldep8mod2 reldep8mod3 \
- reldep9mod1 reldep9mod2 reldep9mod3 \
- tst-alignmod tst-alignmod2 \
- $(modules-execstack-$(have-z-execstack)) \
- tst-dlopenrpathmod tst-deep1mod1 tst-deep1mod2 tst-deep1mod3 \
- tst-dlmopen1mod tst-auditmod1 \
- unload3mod1 unload3mod2 unload3mod3 unload3mod4 \
- unload4mod1 unload4mod2 unload4mod3 unload4mod4 \
- unload6mod1 unload6mod2 unload6mod3 \
- unload7mod1 unload7mod2 \
- unload8mod1 unload8mod1x unload8mod2 unload8mod3 \
- order2mod1 order2mod2 order2mod3 order2mod4 \
- tst-unique1mod1 tst-unique1mod2 \
- tst-unique2mod1 tst-unique2mod2 \
- tst-auditmod9a tst-auditmod9b \
- $(if $(CXX),tst-unique3lib tst-unique3lib2 tst-unique4lib \
- tst-nodelete-uniquemod tst-nodelete-rtldmod \
- tst-nodelete-zmod) \
- tst-initordera1 tst-initorderb1 \
- tst-initordera2 tst-initorderb2 \
- tst-initordera3 tst-initordera4 \
- tst-initorder2a tst-initorder2b tst-initorder2c \
- tst-initorder2d \
- tst-relsort1mod1 tst-relsort1mod2 tst-array2dep \
- tst-array5dep tst-null-argv-lib \
- tst-tlsalign-lib tst-nodelete-opened-lib tst-nodelete2mod \
- tst-audit11mod1 tst-audit11mod2 tst-auditmod11 \
- tst-audit12mod1 tst-audit12mod2 tst-audit12mod3 tst-auditmod12 \
- tst-latepthreadmod $(tst-tls-many-dynamic-modules) \
- tst-nodelete-dlclose-dso tst-nodelete-dlclose-plugin
-ifeq (yes,$(have-mtls-dialect-gnu2))
-tests += tst-gnu2-tls1
-modules-names += tst-gnu2-tls1mod
-$(objpfx)tst-gnu2-tls1: $(objpfx)tst-gnu2-tls1mod.so
-tst-gnu2-tls1mod.so-no-z-defs = yes
-CFLAGS-tst-gnu2-tls1mod.c += -mtls-dialect=gnu2
-endif
-ifeq (yes,$(have-protected-data))
-modules-names += tst-protected1moda tst-protected1modb
-tests += tst-protected1a tst-protected1b
-$(objpfx)tst-protected1a: $(addprefix $(objpfx),tst-protected1moda.so tst-protected1modb.so)
-$(objpfx)tst-protected1b: $(addprefix $(objpfx),tst-protected1modb.so tst-protected1moda.so)
-tst-protected1modb.so-no-z-defs = yes
-# These tests fail with GCC versions prior to 5.1 and with some versions
-# of binutils. See https://sourceware.org/bugzilla/show_bug.cgi?id=17709
-# and https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65248 for details.
-# Perhaps in future we can make these XFAILs conditional on some detection
-# of compiler/linker behavior/version.
-test-xfail-tst-protected1a = yes
-test-xfail-tst-protected1b = yes
-endif
-ifeq (yesyes,$(have-fpie)$(build-shared))
-modules-names += tst-piemod1
-tests += tst-pie1 tst-pie2
-tests-pie += tst-pie1 tst-pie2
-tests += vismain
-tests-pie += vismain
-CFLAGS-vismain.c = $(PIE-ccflag)
-endif
-modules-execstack-yes = tst-execstack-mod
-extra-test-objs += $(addsuffix .os,$(strip $(modules-names)))
-
-# filtmod1.so has a special rule
-modules-names-nobuild := filtmod1
-
-tests += $(tests-static)
-
-ifneq (no,$(multi-arch))
-tests-ifuncstatic := ifuncmain1static ifuncmain1picstatic \
- ifuncmain2static ifuncmain2picstatic \
- ifuncmain4static ifuncmain4picstatic \
- ifuncmain5static ifuncmain5picstatic \
- ifuncmain7static ifuncmain7picstatic
-tests-static += $(tests-ifuncstatic)
-tests-internal += $(tests-ifuncstatic)
-ifeq (yes,$(build-shared))
-tests-internal += \
- ifuncmain1 ifuncmain1pic ifuncmain1vis ifuncmain1vispic \
- ifuncmain1staticpic \
- ifuncmain2 ifuncmain2pic ifuncmain3 ifuncmain4 \
- ifuncmain5 ifuncmain5pic ifuncmain5staticpic \
- ifuncmain7 ifuncmain7pic
-ifunc-test-modules = ifuncdep1 ifuncdep1pic ifuncdep2 ifuncdep2pic \
- ifuncdep5 ifuncdep5pic
-extra-test-objs += $(ifunc-test-modules:=.o)
-test-internal-extras += $(ifunc-test-modules)
-ifeq (yes,$(have-fpie))
-ifunc-pie-tests = ifuncmain1pie ifuncmain1vispie ifuncmain1staticpie \
- ifuncmain5pie ifuncmain6pie ifuncmain7pie
-tests-internal += $(ifunc-pie-tests)
-tests-pie += $(ifunc-pie-tests)
-endif
-modules-names += ifuncmod1 ifuncmod3 ifuncmod5 ifuncmod6
-endif
-endif
-
-ifeq (yes,$(build-shared))
-ifeq ($(run-built-tests),yes)
-tests-special += $(objpfx)tst-pathopt.out $(objpfx)tst-rtld-load-self.out
-endif
-tests-special += $(objpfx)check-textrel.out $(objpfx)check-execstack.out \
- $(objpfx)check-localplt.out
-endif
-
-ifeq ($(run-built-tests),yes)
-tests-special += $(objpfx)order-cmp.out $(objpfx)tst-array1-cmp.out \
- $(objpfx)tst-array1-static-cmp.out \
- $(objpfx)tst-array2-cmp.out $(objpfx)tst-array3-cmp.out \
- $(objpfx)tst-array4-cmp.out $(objpfx)tst-array5-cmp.out \
- $(objpfx)tst-array5-static-cmp.out $(objpfx)order2-cmp.out \
- $(objpfx)tst-initorder-cmp.out \
- $(objpfx)tst-initorder2-cmp.out $(objpfx)tst-unused-dep.out \
- $(objpfx)tst-unused-dep-cmp.out
-endif
-
-check-abi: $(objpfx)check-abi-ld.out
-tests-special += $(objpfx)check-abi-ld.out
-update-abi: update-abi-ld
-update-all-abi: update-all-abi-ld
-
-ifeq ($(have-glob-dat-reloc),yes)
-tests += tst-prelink
-ifeq ($(run-built-tests),yes)
-tests-special += $(objpfx)tst-prelink-cmp.out
-endif
-endif
-
-# The test requires shared _and_ PIE because the executable
-# unit test driver must be able to link with the shared object
-# that is going to eventually go into an installed DSO.
-ifeq (yesyes,$(have-fpie)$(build-shared))
-tests-internal += tst-_dl_addr_inside_object
-tests-pie += tst-_dl_addr_inside_object
-$(objpfx)tst-_dl_addr_inside_object: $(objpfx)dl-addr-obj.os
-CFLAGS-tst-_dl_addr_inside_object.c += $(PIE-ccflag)
-endif
-
-# By default tst-linkall-static should try to use crypt routines to test
-# static libcrypt use.
-CFLAGS-tst-linkall-static.c = -DUSE_CRYPT=1
-# However, if we are using NSS crypto and we don't have a static
-# library, then we exclude the use of crypt functions in the test.
-# We similarly exclude libcrypt.a from the static link (see below).
-ifeq (yesno,$(nss-crypt)$(static-nss-crypt))
-CFLAGS-tst-linkall-static.c = -DUSE_CRYPT=0
-endif
-
-include ../Rules
-
-ifeq (yes,$(build-shared))
-# Make sure these things are built in the `make lib' pass so they can be used
-# to run programs during the `make others' pass.
-lib-noranlib: $(objpfx)$(rtld-installed-name) \
- $(addprefix $(objpfx),$(extra-objs))
-endif
-
-# Command to link into a larger single relocatable object.
-reloc-link = $(LINK.o) -nostdlib -nostartfiles -r
-
-$(objpfx)sotruss-lib.so: $(shlib-lds)
-
-$(objpfx)dl-allobjs.os: $(all-rtld-routines:%=$(objpfx)%.os)
- $(reloc-link) -o $@ $^
-
-# Link together the dynamic linker into a single relocatable object.
-# First we do a link against libc_pic.a just to get a link map,
-# and discard the object produced by that link. From the link map
-# we can glean all the libc modules that need to go into the dynamic
-# linker. Then we do a recursive make that goes into all the subdirs
-# those modules come from and builds special rtld-foo.os versions that
-# are compiled with special flags, and puts these modules into rtld-libc.a
-# for us. Then we do the real link using rtld-libc.a instead of libc_pic.a.
-
-# If the compiler can do SSP, build the mapfile with dummy __stack_chk_fail
-# and __stack_chk_fail_local symbols defined, to prevent the real things
-# being dragged into rtld even though rtld is never built with stack-
-# protection.
-
-ifeq ($(have-ssp),yes)
-dummy-stack-chk-fail := -Wl,--defsym='__stack_chk_fail=0' \
- -Wl,--defsym='__stack_chk_fail_local=0'
-else
-dummy-stack-chk-fail :=
-endif
-
-$(objpfx)librtld.map: $(objpfx)dl-allobjs.os $(common-objpfx)libc_pic.a
- @-rm -f $@T
- $(reloc-link) -o $@.o $(dummy-stack-chk-fail) \
- '-Wl,-(' $^ -lgcc '-Wl,-)' -Wl,-Map,$@T
- rm -f $@.o
- mv -f $@T $@
-
-$(objpfx)librtld.mk: $(objpfx)librtld.map Makefile
- LC_ALL=C \
- sed -n 's@^$(common-objpfx)\([^(]*\)(\([^)]*\.os\)) *.*$$@\1 \2@p' \
- $< | \
- while read lib file; do \
- case $$lib in \
- libc_pic.a) \
- LC_ALL=C fgrep -l /$$file \
- $(common-objpfx)stamp.os $(common-objpfx)*/stamp.os | \
- LC_ALL=C \
- sed 's@^$(common-objpfx)\([^/]*\)/stamp\.os$$@rtld-\1'" +=$$file@"\
- ;; \
- */*.a) \
- echo rtld-$${lib%%/*} += $$file ;; \
- *) echo "Wasn't expecting $$lib($$file)" >&2; exit 1 ;; \
- esac; \
- done > $@T
- echo rtld-subdirs = `LC_ALL=C sed 's/^rtld-\([^ ]*\).*$$/\1/' $@T \
- | LC_ALL=C sort -u` >> $@T
- mv -f $@T $@
-
-$(objpfx)rtld-libc.a: $(objpfx)librtld.mk FORCE
- $(MAKE) -f $< -f rtld-Rules
-
-$(objpfx)librtld.os: $(objpfx)dl-allobjs.os $(objpfx)rtld-libc.a
- $(LINK.o) -nostdlib -nostartfiles -r -o $@ '-Wl,-(' $^ -lgcc '-Wl,-)' \
- -Wl,-Map,$@.map
-
-generated += librtld.map librtld.mk rtld-libc.a librtld.os.map
-
-z-now-yes = -Wl,-z,now
-
-$(objpfx)ld.so: $(objpfx)librtld.os $(ld-map)
-# Link into a temporary file so that we don't touch $@ at all
-# if the sanity check below fails.
- $(LINK.o) -nostdlib -nostartfiles -shared -o $@.new \
- $(LDFLAGS-rtld) -Wl,-z,defs $(z-now-$(bind-now)) \
- $(filter-out $(map-file),$^) $(load-map-file) \
- -Wl,-soname=$(rtld-installed-name) \
- -Wl,-defsym=_begin=0
- $(call after-link,$@.new)
- $(READELF) -s $@.new \
- | $(AWK) '($$7 ~ /^UND(|EF)$$/ && $$1 != "0:" && $$4 != "REGISTER") { print; p=1 } END { exit p != 0 }'
- mv -f $@.new $@
-
-ifeq (yes,$(build-shared))
-# interp.c exists just to get the runtime linker path into libc.so.
-$(objpfx)interp.os: $(common-objpfx)runtime-linker.h
-endif
-
-ifneq (ld.so,$(rtld-installed-name))
-# Make sure ld.so.1 exists in the build directory so we can link
-# against it.
-$(objpfx)$(rtld-installed-name): $(objpfx)ld.so
- $(make-link)
-generated += $(rtld-installed-name)
-endif
-
-# Build a file mentioning all trustworthy directories to look for shared
-# libraries when using LD_LIBRARY_PATH in a setuid program. The user can
-# add directories to the list by defining $(user-defined-trusted-dirs)
-# before starting make.
-$(objpfx)trusted-dirs.h: $(objpfx)trusted-dirs.st; @:
-$(objpfx)trusted-dirs.st: Makefile $(..)Makeconfig
- $(make-target-directory)
- echo "$(subst :, ,$(default-rpath) $(user-defined-trusted-dirs))" \
- | $(AWK) -f gen-trusted-dirs.awk > ${@:st=T};
- echo '#define DL_DST_LIB "$(notdir $(slibdir))"' >> ${@:st=T}
- $(move-if-change) ${@:st=T} ${@:st=h}
- touch $@
-CPPFLAGS-dl-load.c = -I$(objpfx). -I$(csu-objpfx).
-
-ifeq (yes,$(build-shared))
-$(inst_slibdir)/$(rtld-version-installed-name): $(objpfx)ld.so $(+force)
- $(make-target-directory)
- $(do-install-program)
-
-$(inst_rtlddir)/$(rtld-installed-name): \
- $(inst_slibdir)/$(rtld-version-installed-name) \
- $(inst_slibdir)/libc-$(version).so
- $(make-target-directory)
- $(make-shlib-link)
-
-# Special target called by parent to install just the dynamic linker.
-.PHONY: ldso_install
-ldso_install: $(inst_rtlddir)/$(rtld-installed-name)
-endif
-
-
-ldd-rewrite = -e 's%@RTLD@%$(rtlddir)/$(rtld-installed-name)%g' \
- -e 's%@VERSION@%$(version)%g' \
- -e 's|@PKGVERSION@|$(PKGVERSION)|g' \
- -e 's|@REPORT_BUGS_TO@|$(REPORT_BUGS_TO)|g' \
- -e 's%@BASH@%$(BASH)%g' \
- -e 's%@TEXTDOMAINDIR@%$(localedir)%g'
-
-ifeq ($(ldd-rewrite-script),no)
-define gen-ldd
-LC_ALL=C sed $(ldd-rewrite) < $< > $@.new
-endef
-else
-define gen-ldd
-LC_ALL=C sed $(ldd-rewrite) < $< \
-| LC_ALL=C sed -f $(patsubst $(..)/%,/%,$(..)$(ldd-rewrite-script)) > $@.new
-endef
-endif
-
-$(objpfx)ldd: ldd.bash.in $(common-objpfx)soversions.mk \
- $(common-objpfx)config.make
- $(gen-ldd)
- chmod 555 $@.new
- mv -f $@.new $@
-
-$(objpfx)sprof: $(libdl)
-
-$(objpfx)sln: $(sln-modules:%=$(objpfx)%.o)
-
-$(objpfx)ldconfig: $(ldconfig-modules:%=$(objpfx)%.o)
-
-SYSCONF-FLAGS := -D'SYSCONFDIR="$(sysconfdir)"'
-CFLAGS-ldconfig.c = $(SYSCONF-FLAGS) -D'LIBDIR="$(libdir)"' \
- -D'SLIBDIR="$(slibdir)"'
-libof-ldconfig = ldconfig
-CFLAGS-dl-cache.c = $(SYSCONF-FLAGS)
-CFLAGS-cache.c = $(SYSCONF-FLAGS)
-CFLAGS-rtld.c = $(SYSCONF-FLAGS)
-
-cpp-srcs-left := $(all-rtld-routines:=.os)
-lib := rtld
-include $(patsubst %,$(..)libof-iterator.mk,$(cpp-srcs-left))
-
-test-modules = $(addprefix $(objpfx),$(addsuffix .so,$(strip $(modules-names))))
-generated += $(addsuffix .so,$(strip $(modules-names)))
-
-$(objpfx)testobj1.so: $(libdl)
-$(objpfx)testobj1_1.so: $(objpfx)testobj1.so $(libdl)
-$(objpfx)testobj2.so: $(objpfx)testobj1.so $(libdl)
-$(objpfx)testobj3.so: $(libdl)
-$(objpfx)testobj4.so: $(libdl)
-$(objpfx)testobj5.so: $(libdl)
-$(objpfx)testobj6.so: $(objpfx)testobj1.so $(objpfx)testobj2.so $(libdl)
-$(objpfx)failobj.so: $(objpfx)testobj6.so
-$(objpfx)dep1.so: $(objpfx)dep2.so $(objpfx)dep4.so
-$(objpfx)dep2.so: $(objpfx)dep3.so $(objpfx)dep4.so
-$(objpfx)dep4.so: $(objpfx)dep3.so
-$(objpfx)nodelmod3.so: $(objpfx)nodelmod4.so
-$(objpfx)nextmod1.so: $(libdl)
-$(objpfx)neededobj1.so: $(libdl)
-$(objpfx)neededobj2.so: $(objpfx)neededobj1.so $(libdl)
-$(objpfx)neededobj3.so: $(objpfx)neededobj1.so $(objpfx)neededobj2.so $(libdl)
-$(objpfx)neededobj4.so: $(objpfx)neededobj1.so $(objpfx)neededobj2.so \
- $(objpfx)neededobj3.so $(libdl)
-$(objpfx)neededobj6.so: $(objpfx)neededobj5.so
-$(objpfx)unload2mod.so: $(objpfx)unload2dep.so
-$(objpfx)ltglobmod2.so: $(libdl)
-$(objpfx)firstobj.so: $(shared-thread-library)
-$(objpfx)globalmod1.so: $(libdl)
-$(objpfx)reldep4mod1.so: $(objpfx)reldep4mod3.so
-$(objpfx)reldep4mod2.so: $(objpfx)reldep4mod4.so
-$(objpfx)dblloadmod1.so: $(objpfx)dblloadmod3.so
-$(objpfx)dblloadmod2.so: $(objpfx)dblloadmod3.so
-$(objpfx)reldepmod5.so: $(objpfx)reldepmod2.so
-$(objpfx)reldepmod6.so: $(objpfx)reldepmod2.so
-$(objpfx)reldep6mod1.so: $(objpfx)reldep6mod0.so
-$(objpfx)reldep6mod2.so: $(objpfx)reldep6mod1.so
-$(objpfx)reldep6mod3.so: $(objpfx)reldep6mod2.so
-$(objpfx)reldep6mod4.so: $(objpfx)reldep6mod1.so
-$(objpfx)tst-tlsmod3.so: $(objpfx)tst-tlsmod2.so
-$(objpfx)tst-tlsmod8.so: $(objpfx)tst-tlsmod7.so
-$(objpfx)tst-tlsmod10.so: $(objpfx)tst-tlsmod9.so
-$(objpfx)tst-tlsmod12.so: $(objpfx)tst-tlsmod11.so
-$(objpfx)tst-tlsmod13a.so: $(objpfx)tst-tlsmod13.so
-# For tst-tls9-static, make sure the modules it dlopens have libc.so in DT_NEEDED
-$(objpfx)tst-tlsmod5.so: $(common-objpfx)libc.so
-$(objpfx)tst-tlsmod6.so: $(common-objpfx)libc.so
-$(objpfx)tst-tls19mod1.so: $(objpfx)tst-tls19mod2.so $(objpfx)tst-tls19mod3.so
-$(objpfx)tst-tls19mod3.so: $(objpfx)ld.so
-$(objpfx)reldep8mod3.so: $(objpfx)reldep8mod1.so $(objpfx)reldep8mod2.so
-$(objpfx)nodel2mod3.so: $(objpfx)nodel2mod1.so $(objpfx)nodel2mod2.so
-$(objpfx)reldep9mod2.so: $(objpfx)reldep9mod1.so
-$(objpfx)reldep9mod3.so: $(objpfx)reldep9mod1.so $(objpfx)reldep9mod2.so
-$(objpfx)unload3mod1.so: $(objpfx)unload3mod3.so
-$(objpfx)unload3mod2.so: $(objpfx)unload3mod3.so
-$(objpfx)unload3mod3.so: $(objpfx)unload3mod4.so
-$(objpfx)unload4mod1.so: $(objpfx)unload4mod2.so $(objpfx)unload4mod3.so
-$(objpfx)unload4mod2.so: $(objpfx)unload4mod4.so $(objpfx)unload4mod3.so
-$(objpfx)unload6mod1.so: $(libdl)
-$(objpfx)unload6mod2.so: $(libdl)
-$(objpfx)unload6mod3.so: $(libdl)
-$(objpfx)unload7mod1.so: $(libdl)
-$(objpfx)unload7mod2.so: $(objpfx)unload7mod1.so
-$(objpfx)unload8mod1.so: $(objpfx)unload8mod2.so
-$(objpfx)unload8mod2.so: $(objpfx)unload8mod3.so
-$(objpfx)unload8mod3.so: $(libdl)
-$(objpfx)tst-initordera2.so: $(objpfx)tst-initordera1.so
-$(objpfx)tst-initorderb2.so: $(objpfx)tst-initorderb1.so $(objpfx)tst-initordera2.so
-$(objpfx)tst-initordera3.so: $(objpfx)tst-initorderb2.so $(objpfx)tst-initorderb1.so
-$(objpfx)tst-initordera4.so: $(objpfx)tst-initordera3.so
-$(objpfx)tst-initorder: $(objpfx)tst-initordera4.so $(objpfx)tst-initordera1.so $(objpfx)tst-initorderb2.so
-$(objpfx)tst-null-argv: $(objpfx)tst-null-argv-lib.so
-$(objpfx)tst-tlsalign: $(objpfx)tst-tlsalign-lib.so
-$(objpfx)tst-nodelete-opened.out: $(objpfx)tst-nodelete-opened-lib.so
-$(objpfx)tst-nodelete-opened: $(libdl)
-$(objpfx)tst-noload: $(libdl)
-
-$(objpfx)tst-tlsalign-extern: $(objpfx)tst-tlsalign-vars.o
-$(objpfx)tst-tlsalign-extern-static: $(objpfx)tst-tlsalign-vars.o
-
-tst-null-argv-ENV = LD_DEBUG=all LD_DEBUG_OUTPUT=$(objpfx)tst-null-argv.debug.out
-LDFLAGS-nodel2mod3.so = $(no-as-needed)
-LDFLAGS-reldepmod5.so = $(no-as-needed)
-LDFLAGS-reldep6mod1.so = $(no-as-needed)
-LDFLAGS-reldep6mod4.so = $(no-as-needed)
-LDFLAGS-reldep8mod3.so = $(no-as-needed)
-LDFLAGS-unload4mod1.so = $(no-as-needed)
-LDFLAGS-unload4mod2.so = $(no-as-needed)
-LDFLAGS-tst-initorder = $(no-as-needed)
-LDFLAGS-tst-initordera2.so = $(no-as-needed)
-LDFLAGS-tst-initordera3.so = $(no-as-needed)
-LDFLAGS-tst-initordera4.so = $(no-as-needed)
-LDFLAGS-tst-initorderb2.so = $(no-as-needed)
-LDFLAGS-tst-tlsmod5.so = -nostdlib $(no-as-needed)
-LDFLAGS-tst-tlsmod6.so = -nostdlib $(no-as-needed)
-
-testobj1.so-no-z-defs = yes
-testobj3.so-no-z-defs = yes
-testobj4.so-no-z-defs = yes
-testobj5.so-no-z-defs = yes
-testobj6.so-no-z-defs = yes
-failobj.so-no-z-defs = yes
-constload2.so-no-z-defs = yes
-constload3.so-no-z-defs = yes
-nodelmod1.so-no-z-defs = yes
-nodelmod2.so-no-z-defs = yes
-nodelmod4.so-no-z-defs = yes
-nodel2mod2.so-no-z-defs = yes
-reldepmod2.so-no-z-defs = yes
-reldepmod3.so-no-z-defs = yes
-reldepmod4.so-no-z-defs = yes
-reldep4mod4.so-no-z-defs = yes
-reldep4mod2.so-no-z-defs = yes
-ltglobmod2.so-no-z-defs = yes
-dblloadmod3.so-no-z-defs = yes
-tst-tlsmod1.so-no-z-defs = yes
-tst-tlsmod2.so-no-z-defs = yes
-tst-tlsmod3.so-no-z-defs = yes
-tst-tlsmod4.so-no-z-defs = yes
-tst-tlsmod7.so-no-z-defs = yes
-tst-tlsmod8.so-no-z-defs = yes
-tst-tlsmod9.so-no-z-defs = yes
-tst-tlsmod10.so-no-z-defs = yes
-tst-tlsmod12.so-no-z-defs = yes
-tst-tlsmod14a.so-no-z-defs = yes
-tst-tlsmod14b.so-no-z-defs = yes
-tst-tlsmod15a.so-no-z-defs = yes
-tst-tlsmod16b.so-no-z-defs = yes
-circlemod2.so-no-z-defs = yes
-circlemod3.so-no-z-defs = yes
-circlemod3a.so-no-z-defs = yes
-reldep8mod2.so-no-z-defs = yes
-reldep9mod1.so-no-z-defs = yes
-unload3mod4.so-no-z-defs = yes
-unload4mod1.so-no-z-defs = yes
-ifuncmod1.so-no-z-defs = yes
-ifuncmod5.so-no-z-defs = yes
-ifuncmod6.so-no-z-defs = yes
-tst-auditmod9a.so-no-z-defs = yes
-tst-auditmod9b.so-no-z-defs = yes
-tst-nodelete-uniquemod.so-no-z-defs = yes
-tst-nodelete-rtldmod.so-no-z-defs = yes
-tst-nodelete-zmod.so-no-z-defs = yes
-tst-nodelete2mod.so-no-z-defs = yes
-
-ifeq ($(build-shared),yes)
-# Build all the modules even when not actually running test programs.
-tests: $(test-modules)
-endif
-
-$(objpfx)loadtest: $(libdl)
-LDFLAGS-loadtest = -rdynamic
-
-$(objpfx)loadtest.out: $(test-modules)
-
-$(objpfx)neededtest: $(libdl)
-$(objpfx)neededtest.out: $(objpfx)neededobj1.so $(objpfx)neededobj2.so \
- $(objpfx)neededobj3.so
-
-$(objpfx)neededtest2: $(libdl)
-$(objpfx)neededtest2.out: $(objpfx)neededobj1.so $(objpfx)neededobj2.so \
- $(objpfx)neededobj3.so
-
-$(objpfx)neededtest3: $(libdl)
-$(objpfx)neededtest3.out: $(objpfx)neededobj1.so $(objpfx)neededobj2.so \
- $(objpfx)neededobj3.so $(objpfx)neededobj4.so
-
-$(objpfx)neededtest4: $(libdl) $(objpfx)neededobj1.so
-$(objpfx)neededtest4.out: $(objpfx)neededobj5.so $(objpfx)neededobj6.so
-
-$(objpfx)restest1: $(objpfx)testobj1.so $(objpfx)testobj1_1.so $(libdl)
-LDFLAGS-restest1 = -rdynamic
-
-$(objpfx)restest2: $(libdl)
-LDFLAGS-restest2 = -rdynamic
-
-$(objpfx)restest1.out: $(test-modules)
-
-preloadtest-preloads = testobj1 testobj2 testobj3 testobj4 testobj5
-$(objpfx)preloadtest: $(objpfx)testobj6.so
-LDFLAGS-preloadtest = -rdynamic
-$(objpfx)preloadtest.out: $(preloadtest-preloads:%=$(objpfx)%.so)
-preloadtest-ENV = \
- LD_PRELOAD=$(subst $(empty) ,:,$(strip $(preloadtest-preloads:=.so)))
-
-$(objpfx)loadfail: $(libdl)
-LDFLAGS-loadfail = -rdynamic
-
-$(objpfx)loadfail.out: $(objpfx)failobj.so
-
-$(objpfx)multiload: $(libdl)
-LDFLAGS-multiload = -rdynamic
-CFLAGS-multiload.c = -DOBJDIR=\"$(elf-objpfx)\"
-
-$(objpfx)multiload.out: $(objpfx)testobj1.so
-
-$(objpfx)origtest: $(libdl)
-LDFLAGS-origtest = -rdynamic
-$(objpfx)origtest.out: $(objpfx)testobj1.so
-
-ifeq ($(have-thread-library),yes)
-$(objpfx)resolvfail: $(libdl) $(shared-thread-library)
-else
-$(objpfx)resolvfail: $(libdl)
-endif
-
-$(objpfx)constload1: $(libdl)
-$(objpfx)constload1.out: $(objpfx)constload2.so $(objpfx)constload3.so
-
-$(objpfx)circleload1: $(libdl)
-$(objpfx)circleload1.out: $(objpfx)circlemod1.so \
- $(objpfx)circlemod1a.so
-
-$(objpfx)circlemod1.so: $(objpfx)circlemod2.so
-$(objpfx)circlemod2.so: $(objpfx)circlemod3.so
-$(objpfx)circlemod1a.so: $(objpfx)circlemod2a.so
-$(objpfx)circlemod2a.so: $(objpfx)circlemod3a.so
-
-$(objpfx)order: $(addprefix $(objpfx),dep4.so dep3.so dep2.so dep1.so)
-
-$(objpfx)order-cmp.out: $(objpfx)order.out
- (echo "0123456789" | cmp $< -) > $@; \
- $(evaluate-test)
-
-$(objpfx)vismain: $(addprefix $(objpfx),vismod1.so vismod2.so)
-$(objpfx)vismain.out: $(addprefix $(objpfx),vismod3.so)
-vismain-ENV = LD_PRELOAD=$(addprefix $(objpfx),vismod3.so)
-
-$(objpfx)noload: $(objpfx)testobj1.so $(libdl)
-LDFLAGS-noload = -rdynamic $(no-as-needed)
-$(objpfx)noload.out: $(objpfx)testobj5.so
-
-$(objpfx)noload-mem.out: $(objpfx)noload.out
- $(common-objpfx)malloc/mtrace $(objpfx)noload.mtrace > $@; \
- $(evaluate-test)
-noload-ENV = MALLOC_TRACE=$(objpfx)noload.mtrace
-
-LDFLAGS-nodelete = -rdynamic
-LDFLAGS-nodelmod1.so = -Wl,--enable-new-dtags,-z,nodelete
-LDFLAGS-nodelmod4.so = -Wl,--enable-new-dtags,-z,nodelete
-$(objpfx)nodelete: $(libdl)
-$(objpfx)nodelete.out: $(objpfx)nodelmod1.so $(objpfx)nodelmod2.so \
- $(objpfx)nodelmod3.so
-
-LDFLAGS-nodlopenmod.so = -Wl,--enable-new-dtags,-z,nodlopen
-$(objpfx)nodlopen: $(libdl)
-$(objpfx)nodlopen.out: $(objpfx)nodlopenmod.so
-
-$(objpfx)nodlopenmod2.so: $(objpfx)nodlopenmod.so
-$(objpfx)nodlopen2: $(libdl)
-$(objpfx)nodlopen2.out: $(objpfx)nodlopenmod2.so
-
-$(objpfx)filtmod1.so: $(objpfx)filtmod1.os $(objpfx)filtmod2.so
- $(LINK.o) -shared -o $@ -B$(csu-objpfx) $(LDFLAGS.so) \
- -L$(subst :, -L,$(rpath-link)) \
- -Wl,-rpath-link=$(rpath-link) \
- $< -Wl,-F,$(objpfx)filtmod2.so
-$(objpfx)filter: $(objpfx)filtmod1.so
-
-# This does not link against libc.
-CFLAGS-filtmod1.c = $(no-stack-protector)
-
-$(objpfx)unload: $(libdl)
-$(objpfx)unload.out: $(objpfx)unloadmod.so
-
-$(objpfx)reldep: $(libdl)
-$(objpfx)reldep.out: $(objpfx)reldepmod1.so $(objpfx)reldepmod2.so
-
-$(objpfx)reldep2: $(libdl)
-$(objpfx)reldep2.out: $(objpfx)reldepmod1.so $(objpfx)reldepmod3.so
-
-$(objpfx)reldep3: $(libdl)
-$(objpfx)reldep3.out: $(objpfx)reldepmod1.so $(objpfx)reldepmod4.so
-
-$(objpfx)reldep4: $(libdl)
-$(objpfx)reldep4.out: $(objpfx)reldep4mod1.so $(objpfx)reldep4mod2.so
-
-$(objpfx)next: $(objpfx)nextmod1.so $(objpfx)nextmod2.so $(libdl)
-LDFLAGS-next = $(no-as-needed)
-
-$(objpfx)unload2: $(libdl)
-$(objpfx)unload2.out: $(objpfx)unload2mod.so $(objpfx)unload2dep.so
-
-$(objpfx)lateglobal: $(libdl)
-$(objpfx)lateglobal.out: $(objpfx)ltglobmod1.so $(objpfx)ltglobmod2.so
-
-$(objpfx)tst-pathopt: $(libdl)
-$(objpfx)tst-pathopt.out: tst-pathopt.sh $(objpfx)tst-pathopt \
- $(objpfx)pathoptobj.so
- $(SHELL) $< $(common-objpfx) '$(test-wrapper-env)' \
- '$(run-program-env)'; \
- $(evaluate-test)
-
-$(objpfx)tst-rtld-load-self.out: tst-rtld-load-self.sh $(objpfx)ld.so
- $(SHELL) $^ '$(test-wrapper)' '$(test-wrapper-env)' > $@; \
- $(evaluate-test)
-
-$(objpfx)initfirst: $(libdl)
-$(objpfx)initfirst.out: $(objpfx)firstobj.so
-
-$(objpfx)global: $(objpfx)globalmod1.so
-$(objpfx)global.out: $(objpfx)reldepmod1.so
-
-$(objpfx)dblload: $(libdl)
-$(objpfx)dblload.out: $(objpfx)dblloadmod1.so $(objpfx)dblloadmod2.so
-
-$(objpfx)dblunload: $(libdl)
-$(objpfx)dblunload.out: $(objpfx)dblloadmod1.so $(objpfx)dblloadmod2.so
-
-$(objpfx)reldep5: $(libdl)
-$(objpfx)reldep5.out: $(objpfx)reldepmod5.so $(objpfx)reldepmod6.so
-
-$(objpfx)reldep6: $(libdl)
-$(objpfx)reldep6.out: $(objpfx)reldep6mod3.so $(objpfx)reldep6mod4.so
-
-$(objpfx)reldep7: $(libdl)
-$(objpfx)reldep7.out: $(objpfx)reldep7mod1.so $(objpfx)reldep7mod2.so
-
-$(objpfx)reldep8: $(libdl)
-$(objpfx)reldep8.out: $(objpfx)reldep8mod3.so
-
-LDFLAGS-nodel2mod2.so = -Wl,--enable-new-dtags,-z,nodelete
-$(objpfx)nodelete2: $(libdl)
-$(objpfx)nodelete2.out: $(objpfx)nodel2mod3.so
-
-$(objpfx)reldep9: $(libdl)
-$(objpfx)reldep9.out: $(objpfx)reldep9mod3.so
-
-$(objpfx)tst-tls3: $(objpfx)tst-tlsmod1.so
-
-$(objpfx)tst-tls4: $(libdl)
-$(objpfx)tst-tls4.out: $(objpfx)tst-tlsmod2.so
-
-$(objpfx)tst-tls5: $(libdl)
-$(objpfx)tst-tls5.out: $(objpfx)tst-tlsmod2.so
-
-$(objpfx)tst-tls6: $(libdl)
-$(objpfx)tst-tls6.out: $(objpfx)tst-tlsmod2.so
-
-$(objpfx)tst-tls7: $(libdl)
-$(objpfx)tst-tls7.out: $(objpfx)tst-tlsmod3.so
-
-$(objpfx)tst-tls8: $(libdl)
-$(objpfx)tst-tls8.out: $(objpfx)tst-tlsmod3.so $(objpfx)tst-tlsmod4.so
-
-$(objpfx)tst-tls9: $(libdl)
-$(objpfx)tst-tls9.out: $(objpfx)tst-tlsmod5.so $(objpfx)tst-tlsmod6.so
-
-$(objpfx)tst-tls10: $(objpfx)tst-tlsmod8.so $(objpfx)tst-tlsmod7.so
-
-$(objpfx)tst-tls11: $(objpfx)tst-tlsmod10.so $(objpfx)tst-tlsmod9.so
-
-$(objpfx)tst-tls12: $(objpfx)tst-tlsmod12.so $(objpfx)tst-tlsmod11.so
-
-$(objpfx)tst-tls13: $(libdl)
-$(objpfx)tst-tls13.out: $(objpfx)tst-tlsmod13a.so
-
-$(objpfx)tst-tls14: $(objpfx)tst-tlsmod14a.so $(libdl)
-$(objpfx)tst-tls14.out: $(objpfx)tst-tlsmod14b.so
-
-$(objpfx)tst-tls15: $(libdl)
-$(objpfx)tst-tls15.out: $(objpfx)tst-tlsmod15a.so $(objpfx)tst-tlsmod15b.so
-
-$(objpfx)tst-tls-dlinfo: $(libdl)
-$(objpfx)tst-tls-dlinfo.out: $(objpfx)tst-tlsmod2.so
-
-
-
-$(objpfx)tst-tls16: $(libdl)
-$(objpfx)tst-tls16.out: $(objpfx)tst-tlsmod16a.so $(objpfx)tst-tlsmod16b.so
-
-$(objpfx)tst-tls17: $(libdl)
-$(objpfx)tst-tls17.out: $(objpfx)tst-tlsmod17b.so
-$(patsubst %,$(objpfx)%.os,$(tlsmod17a-modules)): $(objpfx)tst-tlsmod17a%.os: tst-tlsmod17a.c
- $(compile-command.c) -DN=$*
-$(patsubst %,$(objpfx)%.so,$(tlsmod17a-modules)): $(objpfx)tst-tlsmod17a%.so: $(objpfx)ld.so
-$(objpfx)tst-tlsmod17b.so: $(patsubst %,$(objpfx)%.so,$(tlsmod17a-modules))
-
-$(objpfx)tst-tls18: $(libdl)
-$(objpfx)tst-tls18.out: $(patsubst %,$(objpfx)%.so,$(tlsmod18a-modules))
-$(patsubst %,$(objpfx)%.os,$(tlsmod18a-modules)): $(objpfx)tst-tlsmod18a%.os : tst-tlsmod18a.c
- $(compile-command.c) -DN=$*
-$(patsubst %,$(objpfx)%.so,$(tlsmod18a-modules)): $(objpfx)tst-tlsmod18a%.so: $(objpfx)ld.so
-
-$(objpfx)tst-tls19: $(libdl)
-$(objpfx)tst-tls19.out: $(objpfx)tst-tls19mod1.so
-
-CFLAGS-tst-align.c = $(stack-align-test-flags)
-CFLAGS-tst-align2.c = $(stack-align-test-flags)
-CFLAGS-tst-alignmod.c = $(stack-align-test-flags)
-CFLAGS-tst-alignmod2.c = $(stack-align-test-flags)
-$(objpfx)tst-align: $(libdl)
-$(objpfx)tst-align.out: $(objpfx)tst-alignmod.so
-$(objpfx)tst-align2: $(objpfx)tst-alignmod2.so
-
-$(objpfx)unload3: $(libdl)
-$(objpfx)unload3.out: $(objpfx)unload3mod1.so $(objpfx)unload3mod2.so \
- $(objpfx)unload3mod3.so $(objpfx)unload3mod4.so
-
-$(objpfx)unload4: $(libdl)
-$(objpfx)unload4.out: $(objpfx)unload4mod1.so $(objpfx)unload4mod3.so
-
-$(objpfx)unload5: $(libdl)
-$(objpfx)unload5.out: $(objpfx)unload3mod1.so $(objpfx)unload3mod2.so \
- $(objpfx)unload3mod3.so $(objpfx)unload3mod4.so
-
-$(objpfx)unload6: $(libdl)
-$(objpfx)unload6.out: $(objpfx)unload6mod1.so $(objpfx)unload6mod2.so \
- $(objpfx)unload6mod3.so
-
-$(objpfx)unload7: $(libdl)
-$(objpfx)unload7.out: $(objpfx)unload7mod1.so $(objpfx)unload7mod2.so
-unload7-ENV = MALLOC_PERTURB_=85
-
-$(objpfx)unload8: $(libdl)
-$(objpfx)unload8.out: $(objpfx)unload8mod1.so $(objpfx)unload8mod1x.so
-
-ifdef libdl
-$(objpfx)tst-tls9-static: $(common-objpfx)dlfcn/libdl.a
-$(objpfx)tst-tls9-static.out: $(objpfx)tst-tlsmod5.so $(objpfx)tst-tlsmod6.so
-endif
-
-ifeq ($(have-z-execstack),yes)
-$(objpfx)tst-execstack: $(libdl)
-$(objpfx)tst-execstack.out: $(objpfx)tst-execstack-mod.so
-CPPFLAGS-tst-execstack.c = -DUSE_PTHREADS=0
-LDFLAGS-tst-execstack = -Wl,-z,noexecstack
-LDFLAGS-tst-execstack-mod = -Wl,-z,execstack
-
-$(objpfx)tst-execstack-needed: $(objpfx)tst-execstack-mod.so
-LDFLAGS-tst-execstack-needed = -Wl,-z,noexecstack
-
-LDFLAGS-tst-execstack-prog = -Wl,-z,execstack
-CFLAGS-tst-execstack-prog.c += -Wno-trampolines
-CFLAGS-tst-execstack-mod.c += -Wno-trampolines
-endif
-
-LDFLAGS-tst-array2 = $(no-as-needed)
-LDFLAGS-tst-array5 = $(no-as-needed)
-
-$(objpfx)tst-array1-cmp.out: tst-array1.exp $(objpfx)tst-array1.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array1-static-cmp.out: tst-array1.exp \
- $(objpfx)tst-array1-static.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array2: $(objpfx)tst-array2dep.so
-$(objpfx)tst-array2-cmp.out: tst-array2.exp $(objpfx)tst-array2.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array3-cmp.out: tst-array1.exp $(objpfx)tst-array3.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array4: $(libdl)
-$(objpfx)tst-array4.out: $(objpfx)tst-array2dep.so
-$(objpfx)tst-array4-cmp.out: tst-array4.exp $(objpfx)tst-array4.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array5: $(objpfx)tst-array5dep.so
-$(objpfx)tst-array5-cmp.out: tst-array5.exp $(objpfx)tst-array5.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-array5-static-cmp.out: tst-array5-static.exp \
- $(objpfx)tst-array5-static.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-CFLAGS-tst-pie1.c += $(pie-ccflag)
-CFLAGS-tst-pie2.c += $(pie-ccflag)
-
-$(objpfx)tst-piemod1.so: $(libsupport)
-$(objpfx)tst-pie1: $(objpfx)tst-piemod1.so
-
-ifeq (yes,$(build-shared))
-all-built-dso := $(common-objpfx)elf/ld.so $(common-objpfx)libc.so \
- $(filter-out $(common-objpfx)linkobj/libc.so, \
- $(sort $(wildcard $(addprefix $(common-objpfx), \
- */lib*.so \
- iconvdata/*.so))))
-
-$(all-built-dso:=.dyn): %.dyn: %
- @rm -f $@T
- LC_ALL=C $(READELF) -W -d $< > $@T
- test -s $@T
- mv -f $@T $@
-common-generated += $(all-built-dso:$(common-objpfx)%=%.dyn)
-
-$(objpfx)check-textrel.out: $(..)scripts/check-textrel.awk \
- $(all-built-dso:=.dyn)
- LC_ALL=C $(AWK) -f $^ > $@; \
- $(evaluate-test)
-generated += check-textrel.out
-
-$(objpfx)execstack-default: $(first-word $(wildcard $(sysdirs:%=%/stackinfo.h)))
- $(make-target-directory)
- { echo '#include <elf.h>'; \
- echo '#include <stackinfo.h>'; \
- echo '#if (DEFAULT_STACK_PERMS & PF_X) == 0'; \
- echo '@@@execstack-no@@@'; \
- echo '#else'; \
- echo '@@@execstack-yes@@@'; \
- echo '#endif'; } | \
- $(CC) $(CFLAGS) $(CPPFLAGS) -E -x c-header - | \
- sed -n -e 's/^@@@\(.*\)@@@/\1/p' > $@T
- mv -f $@T $@
-generated += execstack-default
-
-$(all-built-dso:=.phdr): %.phdr: %
- @rm -f $@T
- LC_ALL=C $(READELF) -W -l $< > $@T
- test -s $@T
- mv -f $@T $@
-common-generated += $(all-built-dso:$(common-objpfx)%=%.phdr)
-
-$(objpfx)check-execstack.out: $(..)scripts/check-execstack.awk \
- $(objpfx)execstack-default \
- $(all-built-dso:=.phdr)
- LC_ALL=C $(AWK) -f $^ > $@; \
- $(evaluate-test)
-generated += check-execstack.out
-
-$(objpfx)tst-dlmodcount: $(libdl)
-$(objpfx)tst-dlmodcount.out: $(test-modules)
-
-$(all-built-dso:=.jmprel): %.jmprel: % Makefile
- @rm -f $@T
- LC_ALL=C $(READELF) -W -S -d -r $< > $@T
- test -s $@T
- mv -f $@T $@
-common-generated += $(all-built-dso:$(common-objpfx)%=%.jmprel)
-
-localplt-built-dso := $(addprefix $(common-objpfx),\
- libc.so \
- elf/ld.so \
- math/libm.so \
- rt/librt.so \
- dlfcn/libdl.so \
- resolv/libresolv.so \
- crypt/libcrypt.so \
- )
-ifeq ($(build-mathvec),yes)
-localplt-built-dso += $(addprefix $(common-objpfx), mathvec/libmvec.so)
-endif
-ifeq ($(have-thread-library),yes)
-localplt-built-dso += $(filter-out %_nonshared.a, $(shared-thread-library))
-endif
-
-vpath localplt.data $(+sysdep_dirs)
-
-$(objpfx)check-localplt.out: $(..)scripts/check-localplt.awk \
- $(..)scripts/localplt.awk \
- $(localplt-built-dso:=.jmprel) \
- localplt.data
- LC_ALL=C $(AWK) -f $(filter-out $< %localplt.data,$^) | \
- LC_ALL=C $(AWK) -f $< $(filter %localplt.data,$^) - \
- > $@; \
- $(evaluate-test)
-endif
-
-$(objpfx)tst-dlopenrpathmod.so: $(libdl)
-$(objpfx)tst-dlopenrpath: $(objpfx)tst-dlopenrpathmod.so $(libdl)
-CFLAGS-tst-dlopenrpath.c += -DPFX=\"$(objpfx)\"
-LDFLAGS-tst-dlopenrpathmod.so += -Wl,-rpath,\$$ORIGIN/test-subdir
-$(objpfx)tst-dlopenrpath.out: $(objpfx)firstobj.so
-
-$(objpfx)tst-deep1mod2.so: $(objpfx)tst-deep1mod3.so
-$(objpfx)tst-deep1: $(libdl) $(objpfx)tst-deep1mod1.so
-$(objpfx)tst-deep1.out: $(objpfx)tst-deep1mod2.so
-LDFLAGS-tst-deep1 += -rdynamic
-tst-deep1mod3.so-no-z-defs = yes
-
-$(objpfx)tst-dlmopen1mod.so: $(libdl)
-$(objpfx)tst-dlmopen1: $(libdl)
-$(objpfx)tst-dlmopen1.out: $(objpfx)tst-dlmopen1mod.so
-
-$(objpfx)tst-dlmopen2: $(libdl)
-$(objpfx)tst-dlmopen2.out: $(objpfx)tst-dlmopen1mod.so
-
-$(objpfx)tst-dlmopen3: $(libdl)
-$(objpfx)tst-dlmopen3.out: $(objpfx)tst-dlmopen1mod.so
-
-$(objpfx)tst-audit1.out: $(objpfx)tst-auditmod1.so
-tst-audit1-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so
-
-$(objpfx)tst-audit2: $(libdl)
-$(objpfx)tst-audit2.out: $(objpfx)tst-auditmod1.so $(objpfx)tst-auditmod9b.so
-# Prevent GCC-5 from translating a malloc/memset pair into calloc
-CFLAGS-tst-audit2.c += -fno-builtin
-tst-audit2-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so
-
-$(objpfx)tst-audit9: $(libdl)
-$(objpfx)tst-audit9.out: $(objpfx)tst-auditmod9a.so $(objpfx)tst-auditmod9b.so
-tst-audit9-ENV = LD_AUDIT=$(objpfx)tst-auditmod9a.so
-
-$(objpfx)tst-audit8: $(libm)
-$(objpfx)tst-audit8.out: $(objpfx)tst-auditmod1.so
-tst-audit8-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so
-
-$(objpfx)tst-global1: $(libdl)
-$(objpfx)tst-global1.out: $(objpfx)testobj6.so $(objpfx)testobj2.so
-
-$(objpfx)order2: $(libdl)
-$(objpfx)order2.out: $(objpfx)order2mod1.so $(objpfx)order2mod2.so
-$(objpfx)order2-cmp.out: $(objpfx)order2.out
- (echo "12345" | cmp $< -) > $@; \
- $(evaluate-test)
-$(objpfx)order2mod1.so: $(objpfx)order2mod4.so
-$(objpfx)order2mod4.so: $(objpfx)order2mod3.so
-$(objpfx)order2mod2.so: $(objpfx)order2mod3.so
-order2mod2.so-no-z-defs = yes
-LDFLAGS-order2mod1.so = $(no-as-needed)
-LDFLAGS-order2mod2.so = $(no-as-needed)
-
-tst-stackguard1-ARGS = --command "$(host-test-program-cmd) --child"
-tst-stackguard1-static-ARGS = --command "$(objpfx)tst-stackguard1-static --child"
-
-tst-ptrguard1-ARGS = --command "$(host-test-program-cmd) --child"
-# When built statically, the pointer guard interface uses
-# __pointer_chk_guard_local.
-CFLAGS-tst-ptrguard1-static.c = -DPTRGUARD_LOCAL
-tst-ptrguard1-static-ARGS = --command "$(objpfx)tst-ptrguard1-static --child"
-
-$(objpfx)tst-leaks1: $(libdl)
-$(objpfx)tst-leaks1-mem.out: $(objpfx)tst-leaks1.out
- $(common-objpfx)malloc/mtrace $(objpfx)tst-leaks1.mtrace > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-leaks1-static: $(common-objpfx)dlfcn/libdl.a
-$(objpfx)tst-leaks1-static-mem.out: $(objpfx)tst-leaks1-static.out
- $(common-objpfx)malloc/mtrace $(objpfx)tst-leaks1-static.mtrace > $@; \
- $(evaluate-test)
-
-tst-leaks1-ENV = MALLOC_TRACE=$(objpfx)tst-leaks1.mtrace
-tst-leaks1-static-ENV = MALLOC_TRACE=$(objpfx)tst-leaks1-static.mtrace
-
-$(objpfx)tst-addr1: $(libdl)
-
-$(objpfx)tst-thrlock: $(libdl) $(shared-thread-library)
-$(objpfx)tst-dlopen-aout: $(libdl) $(shared-thread-library)
-
-CFLAGS-ifuncmain1pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain1picstatic.c += $(pic-ccflag)
-CFLAGS-ifuncmain1staticpic.c += $(pic-ccflag)
-CFLAGS-ifuncdep1pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain1vispic.c += $(pic-ccflag)
-CFLAGS-ifuncmain2pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain2picstatic.c += $(pic-ccflag)
-CFLAGS-ifuncdep2pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain4picstatic.c += $(pic-ccflag)
-CFLAGS-ifuncmain5pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain5picstatic.c += $(pic-ccflag)
-CFLAGS-ifuncmain5staticpic.c += $(pic-ccflag)
-CFLAGS-ifuncdep5pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain7pic.c += $(pic-ccflag)
-CFLAGS-ifuncmain7picstatic.c += $(pic-ccflag)
-
-LDFLAGS-ifuncmain3 = -Wl,-export-dynamic
-
-CFLAGS-ifuncmain1pie.c += $(pie-ccflag)
-CFLAGS-ifuncmain1vispie.c += $(pie-ccflag)
-CFLAGS-ifuncmain1staticpie.c += $(pie-ccflag)
-CFLAGS-ifuncmain5pie.c += $(pie-ccflag)
-CFLAGS-ifuncmain6pie.c += $(pie-ccflag)
-CFLAGS-ifuncmain7pie.c += $(pie-ccflag)
-
-$(objpfx)ifuncmain1pie: $(objpfx)ifuncmod1.so
-$(objpfx)ifuncmain1staticpie: $(objpfx)ifuncdep1pic.o
-$(objpfx)ifuncmain1vispie: $(objpfx)ifuncmod1.so
-$(objpfx)ifuncmain5pie: $(objpfx)ifuncmod5.so
-$(objpfx)ifuncmain6pie: $(objpfx)ifuncmod6.so
-
-$(objpfx)ifuncmain1: $(addprefix $(objpfx),ifuncmod1.so)
-$(objpfx)ifuncmain1pic: $(addprefix $(objpfx),ifuncmod1.so)
-$(objpfx)ifuncmain1staticpic: $(addprefix $(objpfx),ifuncdep1pic.o)
-$(objpfx)ifuncmain1static: $(addprefix $(objpfx),ifuncdep1.o)
-$(objpfx)ifuncmain1picstatic: $(addprefix $(objpfx),ifuncdep1pic.o)
-$(objpfx)ifuncmain1vis: $(addprefix $(objpfx),ifuncmod1.so)
-$(objpfx)ifuncmain1vispic: $(addprefix $(objpfx),ifuncmod1.so)
-$(objpfx)ifuncmain2: $(addprefix $(objpfx),ifuncdep2.o)
-$(objpfx)ifuncmain2pic: $(addprefix $(objpfx),ifuncdep2pic.o)
-$(objpfx)ifuncmain2static: $(addprefix $(objpfx),ifuncdep2.o)
-$(objpfx)ifuncmain2picstatic: $(addprefix $(objpfx),ifuncdep2pic.o)
-
-$(objpfx)ifuncmain3: $(libdl)
-$(objpfx)ifuncmain3.out: $(objpfx)ifuncmod3.so
-
-$(objpfx)ifuncmain5: $(addprefix $(objpfx),ifuncmod5.so)
-$(objpfx)ifuncmain5pic: $(addprefix $(objpfx),ifuncmod5.so)
-$(objpfx)ifuncmain5static: $(addprefix $(objpfx),ifuncdep5.o)
-$(objpfx)ifuncmain5staticpic: $(addprefix $(objpfx),ifuncdep5pic.o)
-$(objpfx)ifuncmain5picstatic: $(addprefix $(objpfx),ifuncdep5pic.o)
-
-$(objpfx)tst-unique1: $(libdl)
-$(objpfx)tst-unique1.out: $(objpfx)tst-unique1mod1.so \
- $(objpfx)tst-unique1mod2.so
-
-$(objpfx)tst-unique2: $(libdl) $(objpfx)tst-unique2mod1.so
-$(objpfx)tst-unique2.out: $(objpfx)tst-unique2mod2.so
-
-$(objpfx)tst-unique3: $(libdl) $(objpfx)tst-unique3lib.so
-$(objpfx)tst-unique3.out: $(objpfx)tst-unique3lib2.so
-
-$(objpfx)tst-unique4: $(objpfx)tst-unique4lib.so
-
-$(objpfx)tst-nodelete: $(libdl)
-$(objpfx)tst-nodelete.out: $(objpfx)tst-nodelete-uniquemod.so \
- $(objpfx)tst-nodelete-rtldmod.so \
- $(objpfx)tst-nodelete-zmod.so
-
-LDFLAGS-tst-nodelete = -rdynamic
-LDFLAGS-tst-nodelete-zmod.so = -Wl,--enable-new-dtags,-z,nodelete
-
-$(objpfx)tst-nodelete2: $(libdl)
-$(objpfx)tst-nodelete2.out: $(objpfx)tst-nodelete2mod.so
-
-LDFLAGS-tst-nodelete2 = -rdynamic
-
-$(objpfx)tst-initorder-cmp.out: tst-initorder.exp $(objpfx)tst-initorder.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-initorder2: $(objpfx)tst-initorder2a.so $(objpfx)tst-initorder2d.so $(objpfx)tst-initorder2c.so
-$(objpfx)tst-initorder2a.so: $(objpfx)tst-initorder2b.so
-$(objpfx)tst-initorder2b.so: $(objpfx)tst-initorder2c.so
-$(objpfx)tst-initorder2c.so: $(objpfx)tst-initorder2d.so
-LDFLAGS-tst-initorder2 = $(no-as-needed)
-LDFLAGS-tst-initorder2a.so = $(no-as-needed)
-LDFLAGS-tst-initorder2b.so = $(no-as-needed)
-LDFLAGS-tst-initorder2c.so = $(no-as-needed)
-define o-iterator-doit
-$(objpfx)tst-initorder2$o.os: tst-initorder2.c; \
-$$(compile-command.c) -DNAME=\"$o\"
-endef
-object-suffixes-left := a b c d
-include $(o-iterator)
-
-$(objpfx)tst-initorder2-cmp.out: tst-initorder2.exp $(objpfx)tst-initorder2.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-relsort1: $(libdl)
-$(objpfx)tst-relsort1mod1.so: $(libm) $(objpfx)tst-relsort1mod2.so
-$(objpfx)tst-relsort1mod2.so: $(libm)
-$(objpfx)tst-relsort1.out: $(objpfx)tst-relsort1mod1.so \
- $(objpfx)tst-relsort1mod2.so
-
-$(objpfx)tst-unused-dep.out: $(objpfx)testobj1.so
- $(test-wrapper-env) \
- LD_TRACE_LOADED_OBJECTS=1 \
- LD_DEBUG=unused \
- LD_PRELOAD= \
- $(rtld-prefix) \
- $< > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-unused-dep-cmp.out: $(objpfx)tst-unused-dep.out
- cmp $< /dev/null > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-audit11.out: $(objpfx)tst-auditmod11.so $(objpfx)tst-audit11mod1.so
-$(objpfx)tst-audit11: $(libdl)
-tst-audit11-ENV = LD_AUDIT=$(objpfx)tst-auditmod11.so
-$(objpfx)tst-audit11mod1.so: $(objpfx)tst-audit11mod2.so
-LDFLAGS-tst-audit11mod2.so = -Wl,--version-script=tst-audit11mod2.map,-soname,tst-audit11mod2.so
-
-$(objpfx)tst-audit12.out: $(objpfx)tst-auditmod12.so $(objpfx)tst-audit12mod1.so $(objpfx)tst-audit12mod3.so
-$(objpfx)tst-audit12: $(libdl)
-tst-audit12-ENV = LD_AUDIT=$(objpfx)tst-auditmod12.so
-$(objpfx)tst-audit12mod1.so: $(objpfx)tst-audit12mod2.so
-LDFLAGS-tst-audit12mod2.so = -Wl,--version-script=tst-audit12mod2.map
-
-# Override -z defs, so that we can reference an undefined symbol.
-# Force lazy binding for the same reason.
-LDFLAGS-tst-latepthreadmod.so = \
- -Wl,-z,lazy -Wl,--unresolved-symbols=ignore-all
-# Do not optimize sibling calls as the test relies on a JMP_SLOT relocation for
-# function this_function_is_not_defined.
-CFLAGS-tst-latepthreadmod.c = -fno-optimize-sibling-calls
-$(objpfx)tst-latepthreadmod.so: $(shared-thread-library)
-$(objpfx)tst-latepthread: $(libdl)
-$(objpfx)tst-latepthread.out: $(objpfx)tst-latepthreadmod.so
-
-# The test modules are parameterized by preprocessor macros.
-$(patsubst %,$(objpfx)%.os,$(tst-tls-many-dynamic-modules)): \
- $(objpfx)tst-tls-manydynamic%mod.os : tst-tls-manydynamicmod.c
- $(compile-command.c) \
- -DNAME=tls_global_$* -DSETTER=set_value_$* -DGETTER=get_value_$*
-$(objpfx)tst-tls-manydynamic: $(libdl) $(shared-thread-library)
-$(objpfx)tst-tls-manydynamic.out: \
- $(patsubst %,$(objpfx)%.so,$(tst-tls-many-dynamic-modules))
-
-tst-prelink-ENV = LD_TRACE_PRELINKING=1
-
-$(objpfx)tst-prelink-conflict.out: $(objpfx)tst-prelink.out
- grep stdout $< | grep conflict | $(AWK) '{ print $$10, $$11 }' > $@
-
-$(objpfx)tst-prelink-cmp.out: tst-prelink.exp \
- $(objpfx)tst-prelink-conflict.out
- cmp $^ > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-ldconfig-X.out : tst-ldconfig-X.sh $(objpfx)ldconfig
- $(SHELL) $< '$(common-objpfx)' '$(test-wrapper-env)' \
- '$(run-program-env)' > $@; \
- $(evaluate-test)
-
-$(objpfx)tst-dlsym-error: $(libdl)
-
-# Test static linking of all the libraries we can possibly link
-# together. Note that in some configurations this may be less than the
-# complete list of libraries we build but we try to maxmimize this list.
-$(objpfx)tst-linkall-static: \
- $(common-objpfx)math/libm.a \
- $(common-objpfx)resolv/libresolv.a \
- $(common-objpfx)dlfcn/libdl.a \
- $(common-objpfx)login/libutil.a \
- $(common-objpfx)rt/librt.a \
- $(common-objpfx)resolv/libanl.a \
- $(static-thread-library)
-
-# If we are using NSS crypto and we have the ability to link statically
-# then we include libcrypt.a, otherwise we leave out libcrypt.a and
-# link as much as we can into the tst-linkall-static test. This assumes
-# that linking with libcrypt.a does everything required to include the
-# static NSS crypto library.
-ifeq (yesyes,$(nss-crypt)$(static-nss-crypt))
-$(objpfx)tst-linkall-static: \
- $(common-objpfx)crypt/libcrypt.a
-endif
-# If we are not using NSS crypto then we always have the ability to link
-# with libcrypt.a.
-ifeq (no,$(nss-crypt))
-$(objpfx)tst-linkall-static: \
- $(common-objpfx)crypt/libcrypt.a
-endif
-
-# The application depends on the DSO, and the DSO loads the plugin.
-# The plugin also depends on the DSO. This creates the circular
-# dependency via dlopen that we're testing to make sure works.
-$(objpfx)tst-nodelete-dlclose-dso.so: $(libdl)
-$(objpfx)tst-nodelete-dlclose-plugin.so: $(objpfx)tst-nodelete-dlclose-dso.so
-$(objpfx)tst-nodelete-dlclose: $(objpfx)tst-nodelete-dlclose-dso.so
-$(objpfx)tst-nodelete-dlclose.out: $(objpfx)tst-nodelete-dlclose-dso.so \
- $(objpfx)tst-nodelete-dlclose-plugin.so
-
-tst-env-setuid-ENV = MALLOC_CHECK_=2 MALLOC_MMAP_THRESHOLD_=4096 \
- LD_HWCAP_MASK=0x1
-tst-env-setuid-tunables-ENV = \
- GLIBC_TUNABLES=glibc.malloc.check=2:glibc.malloc.mmap_threshold=4096
diff --git a/elf/Versions b/elf/Versions
deleted file mode 100644
index c59facdbd7..0000000000
--- a/elf/Versions
+++ /dev/null
@@ -1,77 +0,0 @@
-libc {
- GLIBC_2.0 {
-%ifdef EXPORT_UNWIND_FIND_FDE
- __deregister_frame_info; __register_frame_info;
-%endif
- }
- GLIBC_2.1 {
- # functions used in other libraries
- _dl_mcount_wrapper; _dl_mcount_wrapper_check;
- }
- GLIBC_2.2.4 {
- dl_iterate_phdr;
- }
-%ifdef EXPORT_UNWIND_FIND_FDE
- # Needed for SHLIB_COMPAT calls using this version.
- GLIBC_2.2.5 {
- }
- GCC_3.0 {
- __deregister_frame_info_bases; __register_frame_info_bases;
- __register_frame_info_table_bases; _Unwind_Find_FDE;
- }
-%endif
- GLIBC_PRIVATE {
- # functions used in other libraries
- _dl_addr;
- _dl_open_hook;
- _dl_sym; _dl_vsym;
- __libc_dlclose; __libc_dlopen_mode; __libc_dlsym;
-
- # Internal error handling support. Interposes the functions in ld.so.
- _dl_signal_error; _dl_catch_error;
- }
-}
-
-ld {
- GLIBC_2.0 {
- # Functions which are interposed from libc.so.
- calloc; free; malloc; realloc;
-
- _r_debug;
- }
- GLIBC_2.1 {
- # functions used in other libraries
- _dl_mcount;
- # historically used by Garbage Collectors
- __libc_stack_end;
- }
- GLIBC_2.3 {
- # runtime interface to TLS
- __tls_get_addr;
- }
- GLIBC_2.4 {
- # stack canary
- __stack_chk_guard;
- }
- GLIBC_PRIVATE {
- # Those are in the dynamic linker, but used by libc.so.
- __libc_enable_secure;
- _dl_allocate_tls; _dl_allocate_tls_init;
- _dl_argv; _dl_find_dso_for_object; _dl_get_tls_static_info;
- _dl_deallocate_tls; _dl_make_stack_executable; _dl_out_of_memory;
- _dl_rtld_di_serinfo; _dl_starting_up;
- _rtld_global; _rtld_global_ro;
-
- # Only here for gdb while a better method is developed.
- _dl_debug_state;
-
- # Pointer protection.
- __pointer_chk_guard;
-
- # Internal error handling support. Interposed by libc.so.
- _dl_signal_error; _dl_catch_error;
-
- # Set value of a tunable.
- __tunable_get_val;
- }
-}
diff --git a/elf/cache.c b/elf/cache.c
deleted file mode 100644
index a76f89281d..0000000000
--- a/elf/cache.c
+++ /dev/null
@@ -1,829 +0,0 @@
-/* Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Andreas Jaeger <aj@suse.de>, 1999.
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published
- by the Free Software Foundation; version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, see <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <error.h>
-#include <dirent.h>
-#include <inttypes.h>
-#include <libgen.h>
-#include <libintl.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdint.h>
-#include <sys/fcntl.h>
-#include <sys/mman.h>
-#include <sys/stat.h>
-#include <sys/types.h>
-
-#include <ldconfig.h>
-#include <dl-cache.h>
-
-struct cache_entry
-{
- char *lib; /* Library name. */
- char *path; /* Path to find library. */
- int flags; /* Flags to indicate kind of library. */
- unsigned int osversion; /* Required OS version. */
- uint64_t hwcap; /* Important hardware capabilities. */
- int bits_hwcap; /* Number of bits set in hwcap. */
- struct cache_entry *next; /* Next entry in list. */
-};
-
-/* List of all cache entries. */
-static struct cache_entry *entries;
-
-static const char *flag_descr[] =
-{ "libc4", "ELF", "libc5", "libc6"};
-
-/* Print a single entry. */
-static void
-print_entry (const char *lib, int flag, unsigned int osversion,
- uint64_t hwcap, const char *key)
-{
- printf ("\t%s (", lib);
- switch (flag & FLAG_TYPE_MASK)
- {
- case FLAG_LIBC4:
- case FLAG_ELF:
- case FLAG_ELF_LIBC5:
- case FLAG_ELF_LIBC6:
- fputs (flag_descr[flag & FLAG_TYPE_MASK], stdout);
- break;
- default:
- fputs (_("unknown"), stdout);
- break;
- }
- switch (flag & FLAG_REQUIRED_MASK)
- {
- case FLAG_SPARC_LIB64:
- fputs (",64bit", stdout);
- break;
- case FLAG_IA64_LIB64:
- fputs (",IA-64", stdout);
- break;
- case FLAG_X8664_LIB64:
- fputs (",x86-64", stdout);
- break;
- case FLAG_S390_LIB64:
- fputs (",64bit", stdout);
- break;
- case FLAG_POWERPC_LIB64:
- fputs (",64bit", stdout);
- break;
- case FLAG_MIPS64_LIBN32:
- fputs (",N32", stdout);
- break;
- case FLAG_MIPS64_LIBN64:
- fputs (",64bit", stdout);
- break;
- case FLAG_X8664_LIBX32:
- fputs (",x32", stdout);
- break;
- case FLAG_ARM_LIBHF:
- fputs (",hard-float", stdout);
- break;
- case FLAG_AARCH64_LIB64:
- fputs (",AArch64", stdout);
- break;
- /* Uses the ARM soft-float ABI. */
- case FLAG_ARM_LIBSF:
- fputs (",soft-float", stdout);
- break;
- case FLAG_MIPS_LIB32_NAN2008:
- fputs (",nan2008", stdout);
- break;
- case FLAG_MIPS64_LIBN32_NAN2008:
- fputs (",N32,nan2008", stdout);
- break;
- case FLAG_MIPS64_LIBN64_NAN2008:
- fputs (",64bit,nan2008", stdout);
- break;
- case 0:
- break;
- default:
- printf (",%d", flag & FLAG_REQUIRED_MASK);
- break;
- }
- if (hwcap != 0)
- printf (", hwcap: %#.16" PRIx64, hwcap);
- if (osversion != 0)
- {
- static const char *const abi_tag_os[] =
- {
- [0] = "Linux",
- [1] = "Hurd",
- [2] = "Solaris",
- [3] = "FreeBSD",
- [4] = "kNetBSD",
- [5] = "Syllable",
- [6] = N_("Unknown OS")
- };
-#define MAXTAG (sizeof abi_tag_os / sizeof abi_tag_os[0] - 1)
- unsigned int os = osversion >> 24;
-
- printf (_(", OS ABI: %s %d.%d.%d"),
- _(abi_tag_os[os > MAXTAG ? MAXTAG : os]),
- (osversion >> 16) & 0xff,
- (osversion >> 8) & 0xff,
- osversion & 0xff);
- }
- printf (") => %s\n", key);
-}
-
-
-/* Print the whole cache file, if a file contains the new cache format
- hidden in the old one, print the contents of the new format. */
-void
-print_cache (const char *cache_name)
-{
- int fd = open (cache_name, O_RDONLY);
- if (fd < 0)
- error (EXIT_FAILURE, errno, _("Can't open cache file %s\n"), cache_name);
-
- struct stat64 st;
- if (fstat64 (fd, &st) < 0
- /* No need to map the file if it is empty. */
- || st.st_size == 0)
- {
- close (fd);
- return;
- }
-
- struct cache_file *cache
- = mmap (NULL, st.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
- if (cache == MAP_FAILED)
- error (EXIT_FAILURE, errno, _("mmap of cache file failed.\n"));
-
- size_t cache_size = st.st_size;
- if (cache_size < sizeof (struct cache_file))
- error (EXIT_FAILURE, 0, _("File is not a cache file.\n"));
-
- struct cache_file_new *cache_new = NULL;
- const char *cache_data;
- int format = 0;
-
- if (memcmp (cache->magic, CACHEMAGIC, sizeof CACHEMAGIC - 1))
- {
- /* This can only be the new format without the old one. */
- cache_new = (struct cache_file_new *) cache;
-
- if (memcmp (cache_new->magic, CACHEMAGIC_NEW, sizeof CACHEMAGIC_NEW - 1)
- || memcmp (cache_new->version, CACHE_VERSION,
- sizeof CACHE_VERSION - 1))
- error (EXIT_FAILURE, 0, _("File is not a cache file.\n"));
- format = 1;
- /* This is where the strings start. */
- cache_data = (const char *) cache_new;
- }
- else
- {
- size_t offset = ALIGN_CACHE (sizeof (struct cache_file)
- + (cache->nlibs
- * sizeof (struct file_entry)));
- /* This is where the strings start. */
- cache_data = (const char *) &cache->libs[cache->nlibs];
-
- /* Check for a new cache embedded in the old format. */
- if (cache_size >
- (offset + sizeof (struct cache_file_new)))
- {
-
- cache_new = (struct cache_file_new *) ((void *)cache + offset);
-
- if (memcmp (cache_new->magic, CACHEMAGIC_NEW,
- sizeof CACHEMAGIC_NEW - 1) == 0
- && memcmp (cache_new->version, CACHE_VERSION,
- sizeof CACHE_VERSION - 1) == 0)
- {
- cache_data = (const char *) cache_new;
- format = 1;
- }
- }
- }
-
- if (format == 0)
- {
- printf (_("%d libs found in cache `%s'\n"), cache->nlibs, cache_name);
-
- /* Print everything. */
- for (unsigned int i = 0; i < cache->nlibs; i++)
- print_entry (cache_data + cache->libs[i].key,
- cache->libs[i].flags, 0, 0,
- cache_data + cache->libs[i].value);
- }
- else if (format == 1)
- {
- printf (_("%d libs found in cache `%s'\n"),
- cache_new->nlibs, cache_name);
-
- /* Print everything. */
- for (unsigned int i = 0; i < cache_new->nlibs; i++)
- print_entry (cache_data + cache_new->libs[i].key,
- cache_new->libs[i].flags,
- cache_new->libs[i].osversion,
- cache_new->libs[i].hwcap,
- cache_data + cache_new->libs[i].value);
- }
- /* Cleanup. */
- munmap (cache, cache_size);
- close (fd);
-}
-
-/* Initialize cache data structures. */
-void
-init_cache (void)
-{
- entries = NULL;
-}
-
-static int
-compare (const struct cache_entry *e1, const struct cache_entry *e2)
-{
- /* We need to swap entries here to get the correct sort order. */
- int res = _dl_cache_libcmp (e2->lib, e1->lib);
- if (res == 0)
- {
- if (e1->flags < e2->flags)
- return 1;
- else if (e1->flags > e2->flags)
- return -1;
- /* Sort by most specific hwcap. */
- else if (e2->bits_hwcap > e1->bits_hwcap)
- return 1;
- else if (e2->bits_hwcap < e1->bits_hwcap)
- return -1;
- else if (e2->hwcap > e1->hwcap)
- return 1;
- else if (e2->hwcap < e1->hwcap)
- return -1;
- if (e2->osversion > e1->osversion)
- return 1;
- if (e2->osversion < e1->osversion)
- return -1;
- }
- return res;
-}
-
-/* Save the contents of the cache. */
-void
-save_cache (const char *cache_name)
-{
- /* The cache entries are sorted already, save them in this order. */
-
- /* Count the length of all strings. */
- /* The old format doesn't contain hwcap entries and doesn't contain
- libraries in subdirectories with hwcaps entries. Count therefore
- also all entries with hwcap == 0. */
- size_t total_strlen = 0;
- struct cache_entry *entry;
- /* Number of cache entries. */
- int cache_entry_count = 0;
- /* Number of normal cache entries. */
- int cache_entry_old_count = 0;
-
- for (entry = entries; entry != NULL; entry = entry->next)
- {
- /* Account the final NULs. */
- total_strlen += strlen (entry->lib) + strlen (entry->path) + 2;
- ++cache_entry_count;
- if (entry->hwcap == 0)
- ++cache_entry_old_count;
- }
-
- /* Create the on disk cache structure. */
- struct cache_file *file_entries = NULL;
- size_t file_entries_size = 0;
-
- if (opt_format != 2)
- {
- /* struct cache_file_new is 64-bit aligned on some arches while
- only 32-bit aligned on other arches. Duplicate last old
- cache entry so that new cache in ld.so.cache can be used by
- both. */
- if (opt_format != 0)
- cache_entry_old_count = (cache_entry_old_count + 1) & ~1;
-
- /* And the list of all entries in the old format. */
- file_entries_size = sizeof (struct cache_file)
- + cache_entry_old_count * sizeof (struct file_entry);
- file_entries = xmalloc (file_entries_size);
-
- /* Fill in the header. */
- memset (file_entries, '\0', sizeof (struct cache_file));
- memcpy (file_entries->magic, CACHEMAGIC, sizeof CACHEMAGIC - 1);
-
- file_entries->nlibs = cache_entry_old_count;
- }
-
- struct cache_file_new *file_entries_new = NULL;
- size_t file_entries_new_size = 0;
-
- if (opt_format != 0)
- {
- /* And the list of all entries in the new format. */
- file_entries_new_size = sizeof (struct cache_file_new)
- + cache_entry_count * sizeof (struct file_entry_new);
- file_entries_new = xmalloc (file_entries_new_size);
-
- /* Fill in the header. */
- memset (file_entries_new, '\0', sizeof (struct cache_file_new));
- memcpy (file_entries_new->magic, CACHEMAGIC_NEW,
- sizeof CACHEMAGIC_NEW - 1);
- memcpy (file_entries_new->version, CACHE_VERSION,
- sizeof CACHE_VERSION - 1);
-
- file_entries_new->nlibs = cache_entry_count;
- file_entries_new->len_strings = total_strlen;
- }
-
- /* Pad for alignment of cache_file_new. */
- size_t pad = ALIGN_CACHE (file_entries_size) - file_entries_size;
-
- /* If we have both formats, we hide the new format in the strings
- table, we have to adjust all string indices for this so that
- old libc5/glibc 2 dynamic linkers just ignore them. */
- unsigned int str_offset;
- if (opt_format != 0)
- str_offset = file_entries_new_size;
- else
- str_offset = 0;
-
- /* An array for all strings. */
- char *strings = xmalloc (total_strlen);
- char *str = strings;
- int idx_old;
- int idx_new;
-
- for (idx_old = 0, idx_new = 0, entry = entries; entry != NULL;
- entry = entry->next, ++idx_new)
- {
- /* First the library. */
- if (opt_format != 2 && entry->hwcap == 0)
- {
- file_entries->libs[idx_old].flags = entry->flags;
- /* XXX: Actually we can optimize here and remove duplicates. */
- file_entries->libs[idx_old].key = str_offset + pad;
- }
- if (opt_format != 0)
- {
- /* We could subtract file_entries_new_size from str_offset -
- not doing so makes the code easier, the string table
- always begins at the beginning of the new cache
- struct. */
- file_entries_new->libs[idx_new].flags = entry->flags;
- file_entries_new->libs[idx_new].osversion = entry->osversion;
- file_entries_new->libs[idx_new].hwcap = entry->hwcap;
- file_entries_new->libs[idx_new].key = str_offset;
- }
-
- size_t len = strlen (entry->lib) + 1;
- str = mempcpy (str, entry->lib, len);
- str_offset += len;
- /* Then the path. */
- if (opt_format != 2 && entry->hwcap == 0)
- file_entries->libs[idx_old].value = str_offset + pad;
- if (opt_format != 0)
- file_entries_new->libs[idx_new].value = str_offset;
- len = strlen (entry->path) + 1;
- str = mempcpy (str, entry->path, len);
- str_offset += len;
- /* Ignore entries with hwcap for old format. */
- if (entry->hwcap == 0)
- ++idx_old;
- }
-
- /* Duplicate last old cache entry if needed. */
- if (opt_format != 2
- && idx_old < cache_entry_old_count)
- file_entries->libs[idx_old] = file_entries->libs[idx_old - 1];
-
- /* Write out the cache. */
-
- /* Write cache first to a temporary file and rename it later. */
- char *temp_name = xmalloc (strlen (cache_name) + 2);
- sprintf (temp_name, "%s~", cache_name);
-
- /* Create file. */
- int fd = open (temp_name, O_CREAT|O_WRONLY|O_TRUNC|O_NOFOLLOW,
- S_IRUSR|S_IWUSR);
- if (fd < 0)
- error (EXIT_FAILURE, errno, _("Can't create temporary cache file %s"),
- temp_name);
-
- /* Write contents. */
- if (opt_format != 2)
- {
- if (write (fd, file_entries, file_entries_size)
- != (ssize_t) file_entries_size)
- error (EXIT_FAILURE, errno, _("Writing of cache data failed"));
- }
- if (opt_format != 0)
- {
- /* Align cache. */
- if (opt_format != 2)
- {
- char zero[pad];
- memset (zero, '\0', pad);
- if (write (fd, zero, pad) != (ssize_t) pad)
- error (EXIT_FAILURE, errno, _("Writing of cache data failed"));
- }
- if (write (fd, file_entries_new, file_entries_new_size)
- != (ssize_t) file_entries_new_size)
- error (EXIT_FAILURE, errno, _("Writing of cache data failed"));
- }
-
- if (write (fd, strings, total_strlen) != (ssize_t) total_strlen
- || close (fd))
- error (EXIT_FAILURE, errno, _("Writing of cache data failed"));
-
- /* Make sure user can always read cache file */
- if (chmod (temp_name, S_IROTH|S_IRGRP|S_IRUSR|S_IWUSR))
- error (EXIT_FAILURE, errno,
- _("Changing access rights of %s to %#o failed"), temp_name,
- S_IROTH|S_IRGRP|S_IRUSR|S_IWUSR);
-
- /* Move temporary to its final location. */
- if (rename (temp_name, cache_name))
- error (EXIT_FAILURE, errno, _("Renaming of %s to %s failed"), temp_name,
- cache_name);
-
- /* Free all allocated memory. */
- free (file_entries_new);
- free (file_entries);
- free (strings);
-
- while (entries)
- {
- entry = entries;
- entries = entries->next;
- free (entry);
- }
-}
-
-
-/* Add one library to the cache. */
-void
-add_to_cache (const char *path, const char *lib, int flags,
- unsigned int osversion, uint64_t hwcap)
-{
- size_t liblen = strlen (lib) + 1;
- size_t len = liblen + strlen (path) + 1;
- struct cache_entry *new_entry
- = xmalloc (sizeof (struct cache_entry) + liblen + len);
-
- new_entry->lib = memcpy ((char *) (new_entry + 1), lib, liblen);
- new_entry->path = new_entry->lib + liblen;
- snprintf (new_entry->path, len, "%s/%s", path, lib);
- new_entry->flags = flags;
- new_entry->osversion = osversion;
- new_entry->hwcap = hwcap;
- new_entry->bits_hwcap = 0;
-
- /* Count the number of bits set in the masked value. */
- for (size_t i = 0;
- (~((1ULL << i) - 1) & hwcap) != 0 && i < 8 * sizeof (hwcap); ++i)
- if ((hwcap & (1ULL << i)) != 0)
- ++new_entry->bits_hwcap;
-
-
- /* Keep the list sorted - search for right place to insert. */
- struct cache_entry *ptr = entries;
- struct cache_entry *prev = entries;
- while (ptr != NULL)
- {
- if (compare (ptr, new_entry) > 0)
- break;
- prev = ptr;
- ptr = ptr->next;
- }
- /* Is this the first entry? */
- if (ptr == entries)
- {
- new_entry->next = entries;
- entries = new_entry;
- }
- else
- {
- new_entry->next = prev->next;
- prev->next = new_entry;
- }
-}
-
-
-/* Auxiliary cache. */
-
-struct aux_cache_entry_id
-{
- uint64_t ino;
- uint64_t ctime;
- uint64_t size;
- uint64_t dev;
-};
-
-struct aux_cache_entry
-{
- struct aux_cache_entry_id id;
- int flags;
- unsigned int osversion;
- int used;
- char *soname;
- struct aux_cache_entry *next;
-};
-
-#define AUX_CACHEMAGIC "glibc-ld.so.auxcache-1.0"
-
-struct aux_cache_file_entry
-{
- struct aux_cache_entry_id id; /* Unique id of entry. */
- int32_t flags; /* This is 1 for an ELF library. */
- uint32_t soname; /* String table indice. */
- uint32_t osversion; /* Required OS version. */
- int32_t pad;
-};
-
-/* ldconfig maintains an auxiliary cache file that allows
- only reading those libraries that have changed since the last iteration.
- For this for each library some information is cached in the auxiliary
- cache. */
-struct aux_cache_file
-{
- char magic[sizeof AUX_CACHEMAGIC - 1];
- uint32_t nlibs; /* Number of entries. */
- uint32_t len_strings; /* Size of string table. */
- struct aux_cache_file_entry libs[0]; /* Entries describing libraries. */
- /* After this the string table of size len_strings is found. */
-};
-
-static const unsigned int primes[] =
-{
- 1021, 2039, 4093, 8191, 16381, 32749, 65521, 131071, 262139,
- 524287, 1048573, 2097143, 4194301, 8388593, 16777213, 33554393,
- 67108859, 134217689, 268435399, 536870909, 1073741789, 2147483647
-};
-
-static size_t aux_hash_size;
-static struct aux_cache_entry **aux_hash;
-
-/* Simplistic hash function for aux_cache_entry_id. */
-static unsigned int
-aux_cache_entry_id_hash (struct aux_cache_entry_id *id)
-{
- uint64_t ret = ((id->ino * 11 + id->ctime) * 11 + id->size) * 11 + id->dev;
- return ret ^ (ret >> 32);
-}
-
-static size_t nextprime (size_t x)
-{
- for (unsigned int i = 0; i < sizeof (primes) / sizeof (primes[0]); ++i)
- if (primes[i] >= x)
- return primes[i];
- return x;
-}
-
-void
-init_aux_cache (void)
-{
- aux_hash_size = primes[3];
- aux_hash = xcalloc (aux_hash_size, sizeof (struct aux_cache_entry *));
-}
-
-int
-search_aux_cache (struct stat64 *stat_buf, int *flags,
- unsigned int *osversion, char **soname)
-{
- struct aux_cache_entry_id id;
- id.ino = (uint64_t) stat_buf->st_ino;
- id.ctime = (uint64_t) stat_buf->st_ctime;
- id.size = (uint64_t) stat_buf->st_size;
- id.dev = (uint64_t) stat_buf->st_dev;
-
- unsigned int hash = aux_cache_entry_id_hash (&id);
- struct aux_cache_entry *entry;
- for (entry = aux_hash[hash % aux_hash_size]; entry; entry = entry->next)
- if (id.ino == entry->id.ino
- && id.ctime == entry->id.ctime
- && id.size == entry->id.size
- && id.dev == entry->id.dev)
- {
- *flags = entry->flags;
- *osversion = entry->osversion;
- if (entry->soname != NULL)
- *soname = xstrdup (entry->soname);
- else
- *soname = NULL;
- entry->used = 1;
- return 1;
- }
-
- return 0;
-}
-
-static void
-insert_to_aux_cache (struct aux_cache_entry_id *id, int flags,
- unsigned int osversion, const char *soname, int used)
-{
- size_t hash = aux_cache_entry_id_hash (id) % aux_hash_size;
- struct aux_cache_entry *entry;
- for (entry = aux_hash[hash]; entry; entry = entry->next)
- if (id->ino == entry->id.ino
- && id->ctime == entry->id.ctime
- && id->size == entry->id.size
- && id->dev == entry->id.dev)
- abort ();
-
- size_t len = soname ? strlen (soname) + 1 : 0;
- entry = xmalloc (sizeof (struct aux_cache_entry) + len);
- entry->id = *id;
- entry->flags = flags;
- entry->osversion = osversion;
- entry->used = used;
- if (soname != NULL)
- entry->soname = memcpy ((char *) (entry + 1), soname, len);
- else
- entry->soname = NULL;
- entry->next = aux_hash[hash];
- aux_hash[hash] = entry;
-}
-
-void
-add_to_aux_cache (struct stat64 *stat_buf, int flags,
- unsigned int osversion, const char *soname)
-{
- struct aux_cache_entry_id id;
- id.ino = (uint64_t) stat_buf->st_ino;
- id.ctime = (uint64_t) stat_buf->st_ctime;
- id.size = (uint64_t) stat_buf->st_size;
- id.dev = (uint64_t) stat_buf->st_dev;
- insert_to_aux_cache (&id, flags, osversion, soname, 1);
-}
-
-/* Load auxiliary cache to search for unchanged entries. */
-void
-load_aux_cache (const char *aux_cache_name)
-{
- int fd = open (aux_cache_name, O_RDONLY);
- if (fd < 0)
- {
- init_aux_cache ();
- return;
- }
-
- struct stat64 st;
- if (fstat64 (fd, &st) < 0 || st.st_size < sizeof (struct aux_cache_file))
- {
- close (fd);
- init_aux_cache ();
- return;
- }
-
- size_t aux_cache_size = st.st_size;
- struct aux_cache_file *aux_cache
- = mmap (NULL, aux_cache_size, PROT_READ, MAP_PRIVATE, fd, 0);
- if (aux_cache == MAP_FAILED
- || aux_cache_size < sizeof (struct aux_cache_file)
- || memcmp (aux_cache->magic, AUX_CACHEMAGIC, sizeof AUX_CACHEMAGIC - 1)
- || aux_cache_size != (sizeof(struct aux_cache_file) +
- aux_cache->nlibs * sizeof(struct aux_cache_file_entry) +
- aux_cache->len_strings))
- {
- close (fd);
- init_aux_cache ();
- return;
- }
-
- aux_hash_size = nextprime (aux_cache->nlibs);
- aux_hash = xcalloc (aux_hash_size, sizeof (struct aux_cache_entry *));
-
- const char *aux_cache_data
- = (const char *) &aux_cache->libs[aux_cache->nlibs];
- for (unsigned int i = 0; i < aux_cache->nlibs; ++i)
- insert_to_aux_cache (&aux_cache->libs[i].id,
- aux_cache->libs[i].flags,
- aux_cache->libs[i].osversion,
- aux_cache->libs[i].soname == 0
- ? NULL : aux_cache_data + aux_cache->libs[i].soname,
- 0);
-
- munmap (aux_cache, aux_cache_size);
- close (fd);
-}
-
-/* Save the contents of the auxiliary cache. */
-void
-save_aux_cache (const char *aux_cache_name)
-{
- /* Count the length of all sonames. We start with empty string. */
- size_t total_strlen = 1;
- /* Number of cache entries. */
- int cache_entry_count = 0;
-
- for (size_t i = 0; i < aux_hash_size; ++i)
- for (struct aux_cache_entry *entry = aux_hash[i];
- entry != NULL; entry = entry->next)
- if (entry->used)
- {
- ++cache_entry_count;
- if (entry->soname != NULL)
- total_strlen += strlen (entry->soname) + 1;
- }
-
- /* Auxiliary cache. */
- size_t file_entries_size
- = sizeof (struct aux_cache_file)
- + cache_entry_count * sizeof (struct aux_cache_file_entry);
- struct aux_cache_file *file_entries
- = xmalloc (file_entries_size + total_strlen);
-
- /* Fill in the header of the auxiliary cache. */
- memset (file_entries, '\0', sizeof (struct aux_cache_file));
- memcpy (file_entries->magic, AUX_CACHEMAGIC, sizeof AUX_CACHEMAGIC - 1);
-
- file_entries->nlibs = cache_entry_count;
- file_entries->len_strings = total_strlen;
-
- /* Initial String offset for auxiliary cache is always after the
- special empty string. */
- unsigned int str_offset = 1;
-
- /* An array for all strings. */
- char *str = (char *) file_entries + file_entries_size;
- *str++ = '\0';
-
- size_t idx = 0;
- for (size_t i = 0; i < aux_hash_size; ++i)
- for (struct aux_cache_entry *entry = aux_hash[i];
- entry != NULL; entry = entry->next)
- if (entry->used)
- {
- file_entries->libs[idx].id = entry->id;
- file_entries->libs[idx].flags = entry->flags;
- if (entry->soname == NULL)
- file_entries->libs[idx].soname = 0;
- else
- {
- file_entries->libs[idx].soname = str_offset;
-
- size_t len = strlen (entry->soname) + 1;
- str = mempcpy (str, entry->soname, len);
- str_offset += len;
- }
- file_entries->libs[idx].osversion = entry->osversion;
- file_entries->libs[idx++].pad = 0;
- }
-
- /* Write out auxiliary cache file. */
- /* Write auxiliary cache first to a temporary file and rename it later. */
-
- char *temp_name = xmalloc (strlen (aux_cache_name) + 2);
- sprintf (temp_name, "%s~", aux_cache_name);
-
- /* Check that directory exists and create if needed. */
- char *dir = strdupa (aux_cache_name);
- dir = dirname (dir);
-
- struct stat64 st;
- if (stat64 (dir, &st) < 0)
- {
- if (mkdir (dir, 0700) < 0)
- goto out_fail;
- }
-
- /* Create file. */
- int fd = open (temp_name, O_CREAT|O_WRONLY|O_TRUNC|O_NOFOLLOW,
- S_IRUSR|S_IWUSR);
- if (fd < 0)
- goto out_fail;
-
- if (write (fd, file_entries, file_entries_size + total_strlen)
- != (ssize_t) (file_entries_size + total_strlen)
- || close (fd))
- {
- unlink (temp_name);
- goto out_fail;
- }
-
- /* Move temporary to its final location. */
- if (rename (temp_name, aux_cache_name))
- unlink (temp_name);
-
-out_fail:
- /* Free allocated memory. */
- free (temp_name);
- free (file_entries);
-}
diff --git a/elf/chroot_canon.c b/elf/chroot_canon.c
deleted file mode 100644
index 78cd6f4a5e..0000000000
--- a/elf/chroot_canon.c
+++ /dev/null
@@ -1,177 +0,0 @@
-/* Return the canonical absolute name of a given file inside chroot.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published
- by the Free Software Foundation; version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, see <http://www.gnu.org/licenses/>. */
-
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <limits.h>
-#include <sys/stat.h>
-#include <errno.h>
-#include <stddef.h>
-#include <stdint.h>
-
-#include <eloop-threshold.h>
-#include <ldconfig.h>
-
-#ifndef PATH_MAX
-#define PATH_MAX 1024
-#endif
-
-/* Return the canonical absolute name of file NAME as if chroot(CHROOT) was
- done first. A canonical name does not contain any `.', `..' components
- nor any repeated path separators ('/') or symlinks. All path components
- must exist and NAME must be absolute filename. The result is malloc'd.
- The returned name includes the CHROOT prefix. */
-
-char *
-chroot_canon (const char *chroot, const char *name)
-{
- char *rpath;
- char *dest;
- char *extra_buf = NULL;
- char *rpath_root;
- const char *start;
- const char *end;
- const char *rpath_limit;
- int num_links = 0;
- size_t chroot_len = strlen (chroot);
-
- if (chroot_len < 1)
- {
- __set_errno (EINVAL);
- return NULL;
- }
-
- rpath = xmalloc (chroot_len + PATH_MAX);
-
- rpath_limit = rpath + chroot_len + PATH_MAX;
-
- rpath_root = (char *) mempcpy (rpath, chroot, chroot_len) - 1;
- if (*rpath_root != '/')
- *++rpath_root = '/';
- dest = rpath_root + 1;
-
- for (start = end = name; *start; start = end)
- {
- struct stat64 st;
-
- /* Skip sequence of multiple path-separators. */
- while (*start == '/')
- ++start;
-
- /* Find end of path component. */
- for (end = start; *end && *end != '/'; ++end)
- /* Nothing. */;
-
- if (end - start == 0)
- break;
- else if (end - start == 1 && start[0] == '.')
- /* nothing */;
- else if (end - start == 2 && start[0] == '.' && start[1] == '.')
- {
- /* Back up to previous component, ignore if at root already. */
- if (dest > rpath_root + 1)
- while ((--dest)[-1] != '/');
- }
- else
- {
- size_t new_size;
-
- if (dest[-1] != '/')
- *dest++ = '/';
-
- if (dest + (end - start) >= rpath_limit)
- {
- ptrdiff_t dest_offset = dest - rpath;
- char *new_rpath;
-
- new_size = rpath_limit - rpath;
- if (end - start + 1 > PATH_MAX)
- new_size += end - start + 1;
- else
- new_size += PATH_MAX;
- new_rpath = (char *) xrealloc (rpath, new_size);
- rpath = new_rpath;
- rpath_limit = rpath + new_size;
-
- dest = rpath + dest_offset;
- }
-
- dest = mempcpy (dest, start, end - start);
- *dest = '\0';
-
- if (lstat64 (rpath, &st) < 0)
- {
- if (*end == '\0')
- goto done;
- goto error;
- }
-
- if (S_ISLNK (st.st_mode))
- {
- char *buf = alloca (PATH_MAX);
- size_t len;
-
- if (++num_links > __eloop_threshold ())
- {
- __set_errno (ELOOP);
- goto error;
- }
-
- ssize_t n = readlink (rpath, buf, PATH_MAX - 1);
- if (n < 0)
- {
- if (*end == '\0')
- goto done;
- goto error;
- }
- buf[n] = '\0';
-
- if (!extra_buf)
- extra_buf = alloca (PATH_MAX);
-
- len = strlen (end);
- if (len >= PATH_MAX - n)
- {
- __set_errno (ENAMETOOLONG);
- goto error;
- }
-
- /* Careful here, end may be a pointer into extra_buf... */
- memmove (&extra_buf[n], end, len + 1);
- name = end = memcpy (extra_buf, buf, n);
-
- if (buf[0] == '/')
- dest = rpath_root + 1; /* It's an absolute symlink */
- else
- /* Back up to previous component, ignore if at root already: */
- if (dest > rpath_root + 1)
- while ((--dest)[-1] != '/');
- }
- }
- }
- done:
- if (dest > rpath_root + 1 && dest[-1] == '/')
- --dest;
- *dest = '\0';
-
- return rpath;
-
- error:
- free (rpath);
- return NULL;
-}
diff --git a/elf/circleload1.c b/elf/circleload1.c
deleted file mode 100644
index 990ff84a84..0000000000
--- a/elf/circleload1.c
+++ /dev/null
@@ -1,166 +0,0 @@
-#include <dlfcn.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-static int
-check_loaded_objects (const char **loaded)
-{
- struct link_map *lm;
- int n;
- int *found = NULL;
- int errors = 0;
-
- for (n = 0; loaded[n]; n++)
- /* NOTHING */;
-
- if (n)
- {
- found = (int *) alloca (sizeof (int) * n);
- memset (found, 0, sizeof (int) * n);
- }
-
- printf(" Name\n");
- printf(" --------------------------------------------------------\n");
- for (lm = MAPS; lm; lm = lm->l_next)
- {
- if (lm->l_name && lm->l_name[0])
- printf(" %s, count = %d\n", lm->l_name, (int) lm->l_direct_opencount);
- if (lm->l_type == lt_loaded && lm->l_name)
- {
- int match = 0;
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (strcmp (basename (loaded[n]), basename (lm->l_name)) == 0)
- {
- found[n] = 1;
- match = 1;
- break;
- }
- }
-
- if (match == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not unloaded\n", lm->l_name);
- }
- }
- }
-
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (found[n] == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not loaded\n", loaded[n]);
- }
- }
-
- return errors;
-}
-
-static int
-load_dso (const char **loading, int undef, int flag)
-{
- void *obj;
- const char *loaded[] = { NULL, NULL, NULL, NULL };
- int errors = 0;
- const char *errstring;
-
- printf ("\nThis is what is in memory now:\n");
- errors += check_loaded_objects (loaded);
-
- printf ("Loading shared object %s: %s\n", loading[0],
- flag == RTLD_LAZY ? "RTLD_LAZY" : "RTLD_NOW");
- obj = dlopen (loading[0], flag);
- if (obj == NULL)
- {
- if (flag == RTLD_LAZY)
- {
- ++errors;
- printf ("ERRORS: dlopen shouldn't fail for RTLD_LAZY\n");
- }
-
- errstring = dlerror ();
- if (strstr (errstring, "undefined symbol") == 0
- || strstr (errstring, "circlemod2_undefined") == 0)
- {
- ++errors;
- printf ("ERRORS: dlopen: `%s': Invalid error string\n",
- errstring);
- }
- else
- printf ("dlopen: %s\n", errstring);
- }
- else
- {
- if (undef && flag == RTLD_NOW)
- {
- ++errors;
- printf ("ERRORS: dlopen shouldn't work for RTLD_NOW\n");
- }
-
- if (!undef)
- {
- int (*func) (void);
-
- func = dlsym (obj, "circlemod1");
- if (func == NULL)
- {
- ++errors;
- printf ("ERRORS: cannot get address of \"circlemod1\": %s\n",
- dlerror ());
- }
- else if (func () != 3)
- {
- ++errors;
- printf ("ERRORS: function \"circlemod1\" returned wrong result\n");
- }
- }
-
- loaded[0] = loading[0];
- loaded[1] = loading[1];
- loaded[2] = loading[2];
- }
- errors += check_loaded_objects (loaded);
-
- if (obj)
- {
- printf ("UnLoading shared object %s\n", loading[0]);
- dlclose (obj);
- loaded[0] = NULL;
- loaded[1] = NULL;
- loaded[2] = NULL;
- errors += check_loaded_objects (loaded);
- }
-
- return errors;
-}
-
-int
-main (void)
-{
- int errors = 0;
- const char *loading[3];
-
- loading[0] = "circlemod1a.so";
- loading[1] = "circlemod2a.so";
- loading[2] = "circlemod3a.so";
- errors += load_dso (loading, 0, RTLD_LAZY);
- errors += load_dso (loading, 0, RTLD_NOW);
-
- loading[0] = "circlemod1.so";
- loading[1] = "circlemod2.so";
- loading[2] = "circlemod3.so";
- errors += load_dso (loading, 1, RTLD_LAZY);
- errors += load_dso (loading, 1, RTLD_NOW);
-
- if (errors != 0)
- printf ("%d errors found\n", errors);
-
- return errors;
-}
diff --git a/elf/circlemod1.c b/elf/circlemod1.c
deleted file mode 100644
index 933ccd3c02..0000000000
--- a/elf/circlemod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int circlemod2 (void);
-
-int
-circlemod1 (void)
-{
- return circlemod2 ();
-}
diff --git a/elf/circlemod1a.c b/elf/circlemod1a.c
deleted file mode 100644
index 45f229136d..0000000000
--- a/elf/circlemod1a.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "circlemod1.c"
diff --git a/elf/circlemod2.c b/elf/circlemod2.c
deleted file mode 100644
index ed8c1175fb..0000000000
--- a/elf/circlemod2.c
+++ /dev/null
@@ -1,9 +0,0 @@
-extern void circlemod2_undefined (void);
-extern int circlemod3 (void);
-
-int
-circlemod2 (void)
-{
- circlemod2_undefined ();
- return circlemod3 ();
-}
diff --git a/elf/circlemod2a.c b/elf/circlemod2a.c
deleted file mode 100644
index dc6410b28b..0000000000
--- a/elf/circlemod2a.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int circlemod3 (void);
-
-int
-circlemod2 (void)
-{
- return circlemod3 ();
-}
diff --git a/elf/circlemod3.c b/elf/circlemod3.c
deleted file mode 100644
index 8d16fe682f..0000000000
--- a/elf/circlemod3.c
+++ /dev/null
@@ -1,14 +0,0 @@
-extern int circlemod1 (void);
-extern int circlemod2 (void);
-
-int
-circlemod3 (void)
-{
- return 3;
-}
-
-int
-circlemod3a (void)
-{
- return circlemod1 () + circlemod2 ();
-}
diff --git a/elf/circlemod3a.c b/elf/circlemod3a.c
deleted file mode 100644
index f1b166ef84..0000000000
--- a/elf/circlemod3a.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "circlemod3.c"
diff --git a/elf/constload1.c b/elf/constload1.c
deleted file mode 100644
index 7381beea88..0000000000
--- a/elf/constload1.c
+++ /dev/null
@@ -1,32 +0,0 @@
-#include <dlfcn.h>
-#include <errno.h>
-#include <error.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- int (*foo) (void);
- void *h;
- int ret;
-
- mtrace ();
-
- h = dlopen ("constload2.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h == NULL)
- error (EXIT_FAILURE, errno, "cannot load module \"constload2.so\"");
- foo = dlsym (h, "foo");
- ret = foo ();
- /* Note that the following dlclose() call cannot unload the objects.
- Due to the introduced relocation dependency constload2.so depends
- on constload3.so and the dependencies of constload2.so on constload3.so
- is not visible to ld.so since it's done using dlopen(). */
- if (dlclose (h) != 0)
- {
- puts ("failed to close");
- exit (EXIT_FAILURE);
- }
- return ret;
-}
diff --git a/elf/constload2.c b/elf/constload2.c
deleted file mode 100644
index bf1bf182f3..0000000000
--- a/elf/constload2.c
+++ /dev/null
@@ -1,50 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-extern int bar (void);
-extern int baz (void);
-extern int foo (void);
-extern void __attribute__ ((__constructor__)) init (void);
-
-void *h;
-
-int
-foo (void)
-{
- return 42 + bar ();
-}
-
-int
-baz (void)
-{
- return -21;
-}
-
-
-void
-__attribute__ ((__constructor__))
-init (void)
-{
- h = dlopen ("constload3.so", RTLD_GLOBAL | RTLD_LAZY);
- if (h == NULL)
- {
- puts ("failed to load constload3");
- exit (1);
- }
- else
- puts ("succeeded loading constload3");
-}
-
-static void
-__attribute__ ((__destructor__))
-fini (void)
-{
- if (dlclose (h) != 0)
- {
- puts ("failed to unload constload3");
- exit (1);
- }
- else
- puts ("succeeded unloading constload3");
-}
diff --git a/elf/constload3.c b/elf/constload3.c
deleted file mode 100644
index 9c37620bba..0000000000
--- a/elf/constload3.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int baz (void);
-extern int bar (void);
-
-int
-bar (void)
-{
- return -21 + baz ();
-}
diff --git a/elf/dblload.c b/elf/dblload.c
deleted file mode 100644
index 52389a60ce..0000000000
--- a/elf/dblload.c
+++ /dev/null
@@ -1,53 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-int
-main (void)
-{
- void *p1;
- void *p2;
- int (*fp) (void);
- int result;
-
- mtrace ();
-
- p1 = dlopen ("dblloadmod1.so", RTLD_LAZY);
- if (p1 == NULL)
- {
- printf ("cannot open dblloadmod1.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- p2 = dlopen ("dblloadmod2.so", RTLD_LAZY);
- if (p1 == NULL)
- {
- printf ("cannot open dblloadmod2.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- fp = dlsym (p1, "foo");
- if (fp == NULL)
- {
- printf ("cannot get function \"foo\": %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- result = fp ();
-
- if (dlclose (p1) != 0)
- {
- printf ("error while closing dblloadmod1.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- if (dlclose (p2) != 0)
- {
- printf ("error while closing dblloadmod2.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- return result;
-}
diff --git a/elf/dblloadmod1.c b/elf/dblloadmod1.c
deleted file mode 100644
index ecec29ec63..0000000000
--- a/elf/dblloadmod1.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int bar (void);
-extern int foo (void);
-
-int
-foo (void)
-{
- return 10 + bar ();
-}
diff --git a/elf/dblloadmod2.c b/elf/dblloadmod2.c
deleted file mode 100644
index 3e20aa941b..0000000000
--- a/elf/dblloadmod2.c
+++ /dev/null
@@ -1,15 +0,0 @@
-extern int bar (void);
-extern int baz (void);
-extern int xyzzy (void);
-
-int
-baz (void)
-{
- return -42;
-}
-
-int
-xyzzy (void)
-{
- return 10 + bar ();
-}
diff --git a/elf/dblloadmod3.c b/elf/dblloadmod3.c
deleted file mode 100644
index 80ac3a6375..0000000000
--- a/elf/dblloadmod3.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int bar (void);
-extern int baz (void);
-
-int
-bar (void)
-{
- return 32 + baz ();
-}
diff --git a/elf/dblunload.c b/elf/dblunload.c
deleted file mode 100644
index ab0b2a5e9e..0000000000
--- a/elf/dblunload.c
+++ /dev/null
@@ -1,53 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-int
-main (void)
-{
- void *p1;
- void *p2;
- int (*fp) (void);
- int result;
-
- mtrace ();
-
- p1 = dlopen ("dblloadmod1.so", RTLD_LAZY);
- if (p1 == NULL)
- {
- printf ("cannot load dblloadmod1.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- p2 = dlopen ("dblloadmod2.so", RTLD_LAZY);
- if (p2 == NULL)
- {
- printf ("cannot load dblloadmod2.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- if (dlclose (p1) != 0)
- {
- printf ("error while closing dblloadmod1.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- fp = dlsym (p2, "xyzzy");
- if (fp == NULL)
- {
- printf ("cannot get function \"xyzzy\": %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- result = fp ();
-
- if (dlclose (p2) != 0)
- {
- printf ("error while closing dblloadmod2.so: %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- return result;
-}
diff --git a/elf/dep1.c b/elf/dep1.c
deleted file mode 100644
index 7ef47adb43..0000000000
--- a/elf/dep1.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <unistd.h>
-
-extern int dep1 (void);
-extern int dep2 (void);
-extern int dep4 (void);
-
-static void
-__attribute__ ((constructor))
-init (void)
-{
- write (1, "3", 1);
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- write (1, "6", 1);
-}
-
-int
-dep1 (void)
-{
- return dep4 () - dep2 ();
-}
diff --git a/elf/dep2.c b/elf/dep2.c
deleted file mode 100644
index 749036a4ec..0000000000
--- a/elf/dep2.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <unistd.h>
-
-extern int dep2 (void);
-extern int dep3 (void);
-extern int dep4 (void);
-
-static void
-__attribute__ ((constructor))
-init (void)
-{
- write (1, "2", 1);
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- write (1, "7", 1);
-}
-
-int
-dep2 (void)
-{
- return dep3 () - dep4 ();
-}
diff --git a/elf/dep3.c b/elf/dep3.c
deleted file mode 100644
index 3df6282009..0000000000
--- a/elf/dep3.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <unistd.h>
-
-extern int dep3 (void);
-
-static void
-__attribute__ ((constructor))
-init (void)
-{
- write (1, "0", 1);
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- write (1, "9\n", 2);
-}
-
-int
-dep3 (void)
-{
- return 42;
-}
diff --git a/elf/dep4.c b/elf/dep4.c
deleted file mode 100644
index c496d6f531..0000000000
--- a/elf/dep4.c
+++ /dev/null
@@ -1,24 +0,0 @@
-#include <unistd.h>
-
-extern int dep3 (void);
-extern int dep4 (void);
-
-static void
-__attribute__ ((constructor))
-init (void)
-{
- write (1, "1", 1);
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- write (1, "8", 1);
-}
-
-int
-dep4 (void)
-{
- return dep3 ();
-}
diff --git a/elf/dl-addr-obj.c b/elf/dl-addr-obj.c
deleted file mode 100644
index 62aa630ce5..0000000000
--- a/elf/dl-addr-obj.c
+++ /dev/null
@@ -1,75 +0,0 @@
-/* Determine if address is inside object load segments.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <link.h>
-#include <elf.h>
-
-/* Return non-zero if ADDR lies within one of L's loadable segments.
- We have three cases we care about.
-
- Case 1: addr is above a segment.
- +==================+<- l_map_end
- | |<- addr
- |------------------|<- l_addr + p_vaddr + p_memsz
- | |
- | |
- |------------------|<- l_addr + p_vaddr
- |------------------|<- l_addr
- | |
- +==================+<- l_map_start
-
- Case 2: addr is within a segments.
- +==================+<- l_map_end
- | |
- |------------------|<- l_addr + p_vaddr + p_memsz
- | |<- addr
- | |
- |------------------|<- l_addr + p_vaddr
- |------------------|<- l_addr
- | |
- +==================+<- l_map_start
-
- Case 3: addr is below a segments.
- +==================+<- l_map_end
- | |
- |------------------|<- l_addr + p_vaddr + p_memsz
- | |
- | |
- |------------------|<- l_addr + p_vaddr
- |------------------|<- l_addr
- | |<- addr
- +==================+<- l_map_start
-
- All the arithmetic is unsigned and we shift all the values down by
- l_addr + p_vaddr and then compare the normalized addr to the range
- of interest i.e. 0 <= addr < p_memsz.
-
-*/
-int
-internal_function
-_dl_addr_inside_object (struct link_map *l, const ElfW(Addr) addr)
-{
- int n = l->l_phnum;
- const ElfW(Addr) reladdr = addr - l->l_addr;
-
- while (--n >= 0)
- if (l->l_phdr[n].p_type == PT_LOAD
- && reladdr - l->l_phdr[n].p_vaddr < l->l_phdr[n].p_memsz)
- return 1;
- return 0;
-}
diff --git a/elf/dl-addr.c b/elf/dl-addr.c
deleted file mode 100644
index 1fac63d1a9..0000000000
--- a/elf/dl-addr.c
+++ /dev/null
@@ -1,146 +0,0 @@
-/* Locate the shared object symbol nearest a given address.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stddef.h>
-#include <ldsodefs.h>
-
-
-static inline void
-__attribute ((always_inline))
-determine_info (const ElfW(Addr) addr, struct link_map *match, Dl_info *info,
- struct link_map **mapp, const ElfW(Sym) **symbolp)
-{
- /* Now we know what object the address lies in. */
- info->dli_fname = match->l_name;
- info->dli_fbase = (void *) match->l_map_start;
-
- /* If this is the main program the information is incomplete. */
- if (__builtin_expect (match->l_name[0], 'a') == '\0'
- && match->l_type == lt_executable)
- info->dli_fname = _dl_argv[0];
-
- const ElfW(Sym) *symtab
- = (const ElfW(Sym) *) D_PTR (match, l_info[DT_SYMTAB]);
- const char *strtab = (const char *) D_PTR (match, l_info[DT_STRTAB]);
-
- ElfW(Word) strtabsize = match->l_info[DT_STRSZ]->d_un.d_val;
-
- const ElfW(Sym) *matchsym = NULL;
- if (match->l_info[DT_ADDRTAGIDX (DT_GNU_HASH) + DT_NUM + DT_THISPROCNUM
- + DT_VERSIONTAGNUM + DT_EXTRANUM + DT_VALNUM] != NULL)
- {
- /* We look at all symbol table entries referenced by the hash
- table. */
- for (Elf_Symndx bucket = 0; bucket < match->l_nbuckets; ++bucket)
- {
- Elf32_Word symndx = match->l_gnu_buckets[bucket];
- if (symndx != 0)
- {
- const Elf32_Word *hasharr = &match->l_gnu_chain_zero[symndx];
-
- do
- {
- /* The hash table never references local symbols so
- we can omit that test here. */
- if ((symtab[symndx].st_shndx != SHN_UNDEF
- || symtab[symndx].st_value != 0)
- && ELFW(ST_TYPE) (symtab[symndx].st_info) != STT_TLS
- && DL_ADDR_SYM_MATCH (match, &symtab[symndx],
- matchsym, addr)
- && symtab[symndx].st_name < strtabsize)
- matchsym = (ElfW(Sym) *) &symtab[symndx];
-
- ++symndx;
- }
- while ((*hasharr++ & 1u) == 0);
- }
- }
- }
- else
- {
- const ElfW(Sym) *symtabend;
- if (match->l_info[DT_HASH] != NULL)
- symtabend = (symtab
- + ((Elf_Symndx *) D_PTR (match, l_info[DT_HASH]))[1]);
- else
- /* There is no direct way to determine the number of symbols in the
- dynamic symbol table and no hash table is present. The ELF
- binary is ill-formed but what shall we do? Use the beginning of
- the string table which generally follows the symbol table. */
- symtabend = (const ElfW(Sym) *) strtab;
-
- for (; (void *) symtab < (void *) symtabend; ++symtab)
- if ((ELFW(ST_BIND) (symtab->st_info) == STB_GLOBAL
- || ELFW(ST_BIND) (symtab->st_info) == STB_WEAK)
- && __glibc_likely (!dl_symbol_visibility_binds_local_p (symtab))
- && ELFW(ST_TYPE) (symtab->st_info) != STT_TLS
- && (symtab->st_shndx != SHN_UNDEF
- || symtab->st_value != 0)
- && DL_ADDR_SYM_MATCH (match, symtab, matchsym, addr)
- && symtab->st_name < strtabsize)
- matchsym = (ElfW(Sym) *) symtab;
- }
-
- if (mapp)
- *mapp = match;
- if (symbolp)
- *symbolp = matchsym;
-
- if (matchsym)
- {
- /* We found a symbol close by. Fill in its name and exact
- address. */
- lookup_t matchl = LOOKUP_VALUE (match);
-
- info->dli_sname = strtab + matchsym->st_name;
- info->dli_saddr = DL_SYMBOL_ADDRESS (matchl, matchsym);
- }
- else
- {
- /* No symbol matches. We return only the containing object. */
- info->dli_sname = NULL;
- info->dli_saddr = NULL;
- }
-}
-
-
-int
-internal_function
-_dl_addr (const void *address, Dl_info *info,
- struct link_map **mapp, const ElfW(Sym) **symbolp)
-{
- const ElfW(Addr) addr = DL_LOOKUP_ADDRESS (address);
- int result = 0;
-
- /* Protect against concurrent loads and unloads. */
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- struct link_map *l = _dl_find_dso_for_object (addr);
-
- if (l)
- {
- determine_info (addr, l, info, mapp, symbolp);
- result = 1;
- }
-
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- return result;
-}
-libc_hidden_def (_dl_addr)
diff --git a/elf/dl-brk.c b/elf/dl-brk.c
deleted file mode 100644
index c37cdfec33..0000000000
--- a/elf/dl-brk.c
+++ /dev/null
@@ -1,5 +0,0 @@
-/* We can use the normal code but we also know the __curbrk is not exported
- from ld.so. */
-extern void *__curbrk attribute_hidden;
-
-#include <brk.c>
diff --git a/elf/dl-cache.c b/elf/dl-cache.c
deleted file mode 100644
index e9632da0b3..0000000000
--- a/elf/dl-cache.c
+++ /dev/null
@@ -1,325 +0,0 @@
-/* Support for reading /etc/ld.so.cache files written by Linux ldconfig.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <sys/mman.h>
-#include <dl-cache.h>
-#include <dl-procinfo.h>
-#include <stdint.h>
-#include <_itoa.h>
-#include <dl-hwcaps.h>
-
-#ifndef _DL_PLATFORMS_COUNT
-# define _DL_PLATFORMS_COUNT 0
-#endif
-
-/* This is the starting address and the size of the mmap()ed file. */
-static struct cache_file *cache;
-static struct cache_file_new *cache_new;
-static size_t cachesize;
-
-/* 1 if cache_data + PTR points into the cache. */
-#define _dl_cache_verify_ptr(ptr) (ptr < cache_data_size)
-
-#define SEARCH_CACHE(cache) \
-/* We use binary search since the table is sorted in the cache file. \
- The first matching entry in the table is returned. \
- It is important to use the same algorithm as used while generating \
- the cache file. */ \
-do \
- { \
- left = 0; \
- right = cache->nlibs - 1; \
- \
- while (left <= right) \
- { \
- __typeof__ (cache->libs[0].key) key; \
- \
- middle = (left + right) / 2; \
- \
- key = cache->libs[middle].key; \
- \
- /* Make sure string table indices are not bogus before using \
- them. */ \
- if (! _dl_cache_verify_ptr (key)) \
- { \
- cmpres = 1; \
- break; \
- } \
- \
- /* Actually compare the entry with the key. */ \
- cmpres = _dl_cache_libcmp (name, cache_data + key); \
- if (__glibc_unlikely (cmpres == 0)) \
- { \
- /* Found it. LEFT now marks the last entry for which we \
- know the name is correct. */ \
- left = middle; \
- \
- /* There might be entries with this name before the one we \
- found. So we have to find the beginning. */ \
- while (middle > 0) \
- { \
- __typeof__ (cache->libs[0].key) key; \
- \
- key = cache->libs[middle - 1].key; \
- /* Make sure string table indices are not bogus before \
- using them. */ \
- if (! _dl_cache_verify_ptr (key) \
- /* Actually compare the entry. */ \
- || _dl_cache_libcmp (name, cache_data + key) != 0) \
- break; \
- --middle; \
- } \
- \
- do \
- { \
- int flags; \
- __typeof__ (cache->libs[0]) *lib = &cache->libs[middle]; \
- \
- /* Only perform the name test if necessary. */ \
- if (middle > left \
- /* We haven't seen this string so far. Test whether the \
- index is ok and whether the name matches. Otherwise \
- we are done. */ \
- && (! _dl_cache_verify_ptr (lib->key) \
- || (_dl_cache_libcmp (name, cache_data + lib->key) \
- != 0))) \
- break; \
- \
- flags = lib->flags; \
- if (_dl_cache_check_flags (flags) \
- && _dl_cache_verify_ptr (lib->value)) \
- { \
- if (best == NULL || flags == GLRO(dl_correct_cache_id)) \
- { \
- HWCAP_CHECK; \
- best = cache_data + lib->value; \
- \
- if (flags == GLRO(dl_correct_cache_id)) \
- /* We've found an exact match for the shared \
- object and no general `ELF' release. Stop \
- searching. */ \
- break; \
- } \
- } \
- } \
- while (++middle <= right); \
- break; \
- } \
- \
- if (cmpres < 0) \
- left = middle + 1; \
- else \
- right = middle - 1; \
- } \
- } \
-while (0)
-
-
-int
-internal_function
-_dl_cache_libcmp (const char *p1, const char *p2)
-{
- while (*p1 != '\0')
- {
- if (*p1 >= '0' && *p1 <= '9')
- {
- if (*p2 >= '0' && *p2 <= '9')
- {
- /* Must compare this numerically. */
- int val1;
- int val2;
-
- val1 = *p1++ - '0';
- val2 = *p2++ - '0';
- while (*p1 >= '0' && *p1 <= '9')
- val1 = val1 * 10 + *p1++ - '0';
- while (*p2 >= '0' && *p2 <= '9')
- val2 = val2 * 10 + *p2++ - '0';
- if (val1 != val2)
- return val1 - val2;
- }
- else
- return 1;
- }
- else if (*p2 >= '0' && *p2 <= '9')
- return -1;
- else if (*p1 != *p2)
- return *p1 - *p2;
- else
- {
- ++p1;
- ++p2;
- }
- }
- return *p1 - *p2;
-}
-
-
-/* Look up NAME in ld.so.cache and return the file name stored there, or null
- if none is found. The cache is loaded if it was not already. If loading
- the cache previously failed there will be no more attempts to load it.
- The caller is responsible for freeing the returned string. The ld.so.cache
- may be unmapped at any time by a completing recursive dlopen and
- this function must take care that it does not return references to
- any data in the mapping. */
-char *
-internal_function
-_dl_load_cache_lookup (const char *name)
-{
- int left, right, middle;
- int cmpres;
- const char *cache_data;
- uint32_t cache_data_size;
- const char *best;
-
- /* Print a message if the loading of libs is traced. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS))
- _dl_debug_printf (" search cache=%s\n", LD_SO_CACHE);
-
- if (cache == NULL)
- {
- /* Read the contents of the file. */
- void *file = _dl_sysdep_read_whole_file (LD_SO_CACHE, &cachesize,
- PROT_READ);
-
- /* We can handle three different cache file formats here:
- - the old libc5/glibc2.0/2.1 format
- - the old format with the new format in it
- - only the new format
- The following checks if the cache contains any of these formats. */
- if (file != MAP_FAILED && cachesize > sizeof *cache
- && memcmp (file, CACHEMAGIC, sizeof CACHEMAGIC - 1) == 0)
- {
- size_t offset;
- /* Looks ok. */
- cache = file;
-
- /* Check for new version. */
- offset = ALIGN_CACHE (sizeof (struct cache_file)
- + cache->nlibs * sizeof (struct file_entry));
-
- cache_new = (struct cache_file_new *) ((void *) cache + offset);
- if (cachesize < (offset + sizeof (struct cache_file_new))
- || memcmp (cache_new->magic, CACHEMAGIC_VERSION_NEW,
- sizeof CACHEMAGIC_VERSION_NEW - 1) != 0)
- cache_new = (void *) -1;
- }
- else if (file != MAP_FAILED && cachesize > sizeof *cache_new
- && memcmp (file, CACHEMAGIC_VERSION_NEW,
- sizeof CACHEMAGIC_VERSION_NEW - 1) == 0)
- {
- cache_new = file;
- cache = file;
- }
- else
- {
- if (file != MAP_FAILED)
- __munmap (file, cachesize);
- cache = (void *) -1;
- }
-
- assert (cache != NULL);
- }
-
- if (cache == (void *) -1)
- /* Previously looked for the cache file and didn't find it. */
- return NULL;
-
- best = NULL;
-
- if (cache_new != (void *) -1)
- {
- uint64_t platform;
-
- /* This is where the strings start. */
- cache_data = (const char *) cache_new;
-
- /* Now we can compute how large the string table is. */
- cache_data_size = (const char *) cache + cachesize - cache_data;
-
- platform = _dl_string_platform (GLRO(dl_platform));
- if (platform != (uint64_t) -1)
- platform = 1ULL << platform;
-
- uint64_t hwcap_mask = GET_HWCAP_MASK();
-
-#define _DL_HWCAP_TLS_MASK (1LL << 63)
- uint64_t hwcap_exclude = ~((GLRO(dl_hwcap) & hwcap_mask)
- | _DL_HWCAP_PLATFORM | _DL_HWCAP_TLS_MASK);
-
- /* Only accept hwcap if it's for the right platform. */
-#define HWCAP_CHECK \
- if (lib->hwcap & hwcap_exclude) \
- continue; \
- if (GLRO(dl_osversion) && lib->osversion > GLRO(dl_osversion)) \
- continue; \
- if (_DL_PLATFORMS_COUNT \
- && (lib->hwcap & _DL_HWCAP_PLATFORM) != 0 \
- && (lib->hwcap & _DL_HWCAP_PLATFORM) != platform) \
- continue
- SEARCH_CACHE (cache_new);
- }
- else
- {
- /* This is where the strings start. */
- cache_data = (const char *) &cache->libs[cache->nlibs];
-
- /* Now we can compute how large the string table is. */
- cache_data_size = (const char *) cache + cachesize - cache_data;
-
-#undef HWCAP_CHECK
-#define HWCAP_CHECK do {} while (0)
- SEARCH_CACHE (cache);
- }
-
- /* Print our result if wanted. */
- if (__builtin_expect (GLRO(dl_debug_mask) & DL_DEBUG_LIBS, 0)
- && best != NULL)
- _dl_debug_printf (" trying file=%s\n", best);
-
- if (best == NULL)
- return NULL;
-
- /* The double copy is *required* since malloc may be interposed
- and call dlopen itself whose completion would unmap the data
- we are accessing. Therefore we must make the copy of the
- mapping data without using malloc. */
- char *temp;
- temp = alloca (strlen (best) + 1);
- strcpy (temp, best);
- return __strdup (temp);
-}
-
-#ifndef MAP_COPY
-/* If the system does not support MAP_COPY we cannot leave the file open
- all the time since this would create problems when the file is replaced.
- Therefore we provide this function to close the file and open it again
- once needed. */
-void
-_dl_unload_cache (void)
-{
- if (cache != NULL && cache != (struct cache_file *) -1)
- {
- __munmap (cache, cachesize);
- cache = NULL;
- }
-}
-#endif
diff --git a/elf/dl-caller.c b/elf/dl-caller.c
deleted file mode 100644
index b4c5335baa..0000000000
--- a/elf/dl-caller.c
+++ /dev/null
@@ -1,86 +0,0 @@
-/* Check whether caller comes from the right place.
- Copyright (C) 2004-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <ldsodefs.h>
-#include <stddef.h>
-#include <caller.h>
-#include <gnu/lib-names.h>
-
-
-int
-attribute_hidden
-_dl_check_caller (const void *caller, enum allowmask mask)
-{
- static const char expected1[] = LIBC_SO;
- static const char expected2[] = LIBDL_SO;
-#ifdef LIBPTHREAD_SO
- static const char expected3[] = LIBPTHREAD_SO;
-#endif
- static const char expected4[] = LD_SO;
-
- for (Lmid_t ns = 0; ns < GL(dl_nns); ++ns)
- for (struct link_map *l = GL(dl_ns)[ns]._ns_loaded; l != NULL;
- l = l->l_next)
- if (caller >= (const void *) l->l_map_start
- && caller < (const void *) l->l_text_end)
- {
- /* The address falls into this DSO's address range. Check the
- name. */
- if ((mask & allow_libc) && strcmp (expected1, l->l_name) == 0)
- return 0;
- if ((mask & allow_libdl) && strcmp (expected2, l->l_name) == 0)
- return 0;
-#ifdef LIBPTHREAD_SO
- if ((mask & allow_libpthread) && strcmp (expected3, l->l_name) == 0)
- return 0;
-#endif
- if ((mask & allow_ldso) && strcmp (expected4, l->l_name) == 0)
- return 0;
-
- struct libname_list *runp = l->l_libname;
-
- while (runp != NULL)
- {
- if ((mask & allow_libc) && strcmp (expected1, runp->name) == 0)
- return 0;
- if ((mask & allow_libdl) && strcmp (expected2, runp->name) == 0)
- return 0;
-#ifdef LIBPTHREAD_SO
- if ((mask & allow_libpthread)
- && strcmp (expected3, runp->name) == 0)
- return 0;
-#endif
- if ((mask & allow_ldso) && strcmp (expected4, runp->name) == 0)
- return 0;
-
- runp = runp->next;
- }
-
- break;
- }
-
- /* Maybe the dynamic linker is not yet on the list. */
- if ((mask & allow_ldso) != 0
- && caller >= (const void *) GL(dl_rtld_map).l_map_start
- && caller < (const void *) GL(dl_rtld_map).l_text_end)
- return 0;
-
- /* No valid caller. */
- return 1;
-}
diff --git a/elf/dl-close.c b/elf/dl-close.c
deleted file mode 100644
index 2b46b7cf8b..0000000000
--- a/elf/dl-close.c
+++ /dev/null
@@ -1,843 +0,0 @@
-/* Close a shared object opened by `_dl_open'.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <dlfcn.h>
-#include <errno.h>
-#include <libintl.h>
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <libc-lock.h>
-#include <ldsodefs.h>
-#include <sys/types.h>
-#include <sys/mman.h>
-#include <sysdep-cancel.h>
-#include <tls.h>
-#include <stap-probe.h>
-
-#include <dl-unmap-segments.h>
-
-
-/* Type of the constructor functions. */
-typedef void (*fini_t) (void);
-
-
-/* Special l_idx value used to indicate which objects remain loaded. */
-#define IDX_STILL_USED -1
-
-
-/* Returns true we an non-empty was found. */
-static bool
-remove_slotinfo (size_t idx, struct dtv_slotinfo_list *listp, size_t disp,
- bool should_be_there)
-{
- if (idx - disp >= listp->len)
- {
- if (listp->next == NULL)
- {
- /* The index is not actually valid in the slotinfo list,
- because this object was closed before it was fully set
- up due to some error. */
- assert (! should_be_there);
- }
- else
- {
- if (remove_slotinfo (idx, listp->next, disp + listp->len,
- should_be_there))
- return true;
-
- /* No non-empty entry. Search from the end of this element's
- slotinfo array. */
- idx = disp + listp->len;
- }
- }
- else
- {
- struct link_map *old_map = listp->slotinfo[idx - disp].map;
-
- /* The entry might still be in its unused state if we are closing an
- object that wasn't fully set up. */
- if (__glibc_likely (old_map != NULL))
- {
- assert (old_map->l_tls_modid == idx);
-
- /* Mark the entry as unused. */
- listp->slotinfo[idx - disp].gen = GL(dl_tls_generation) + 1;
- listp->slotinfo[idx - disp].map = NULL;
- }
-
- /* If this is not the last currently used entry no need to look
- further. */
- if (idx != GL(dl_tls_max_dtv_idx))
- return true;
- }
-
- while (idx - disp > (disp == 0 ? 1 + GL(dl_tls_static_nelem) : 0))
- {
- --idx;
-
- if (listp->slotinfo[idx - disp].map != NULL)
- {
- /* Found a new last used index. */
- GL(dl_tls_max_dtv_idx) = idx;
- return true;
- }
- }
-
- /* No non-entry in this list element. */
- return false;
-}
-
-
-void
-_dl_close_worker (struct link_map *map, bool force)
-{
- /* One less direct use. */
- --map->l_direct_opencount;
-
- /* If _dl_close is called recursively (some destructor call dlclose),
- just record that the parent _dl_close will need to do garbage collection
- again and return. */
- static enum { not_pending, pending, rerun } dl_close_state;
-
- if (map->l_direct_opencount > 0 || map->l_type != lt_loaded
- || dl_close_state != not_pending)
- {
- if (map->l_direct_opencount == 0 && map->l_type == lt_loaded)
- dl_close_state = rerun;
-
- /* There are still references to this object. Do nothing more. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("\nclosing file=%s; direct_opencount=%u\n",
- map->l_name, map->l_direct_opencount);
-
- return;
- }
-
- Lmid_t nsid = map->l_ns;
- struct link_namespaces *ns = &GL(dl_ns)[nsid];
-
- retry:
- dl_close_state = pending;
-
- bool any_tls = false;
- const unsigned int nloaded = ns->_ns_nloaded;
- char used[nloaded];
- char done[nloaded];
- struct link_map *maps[nloaded];
-
- /* Clear DF_1_NODELETE to force object deletion. We don't need to touch
- l_tls_dtor_count because forced object deletion only happens when an
- error occurs during object load. Destructor registration for TLS
- non-POD objects should not have happened till then for this
- object. */
- if (force)
- map->l_flags_1 &= ~DF_1_NODELETE;
-
- /* Run over the list and assign indexes to the link maps and enter
- them into the MAPS array. */
- int idx = 0;
- for (struct link_map *l = ns->_ns_loaded; l != NULL; l = l->l_next)
- {
- l->l_idx = idx;
- maps[idx] = l;
- ++idx;
-
- }
- assert (idx == nloaded);
-
- /* Prepare the bitmaps. */
- memset (used, '\0', sizeof (used));
- memset (done, '\0', sizeof (done));
-
- /* Keep track of the lowest index link map we have covered already. */
- int done_index = -1;
- while (++done_index < nloaded)
- {
- struct link_map *l = maps[done_index];
-
- if (done[done_index])
- /* Already handled. */
- continue;
-
- /* Check whether this object is still used. */
- if (l->l_type == lt_loaded
- && l->l_direct_opencount == 0
- && (l->l_flags_1 & DF_1_NODELETE) == 0
- /* See CONCURRENCY NOTES in cxa_thread_atexit_impl.c to know why
- acquire is sufficient and correct. */
- && atomic_load_acquire (&l->l_tls_dtor_count) == 0
- && !used[done_index])
- continue;
-
- /* We need this object and we handle it now. */
- done[done_index] = 1;
- used[done_index] = 1;
- /* Signal the object is still needed. */
- l->l_idx = IDX_STILL_USED;
-
- /* Mark all dependencies as used. */
- if (l->l_initfini != NULL)
- {
- /* We are always the zeroth entry, and since we don't include
- ourselves in the dependency analysis start at 1. */
- struct link_map **lp = &l->l_initfini[1];
- while (*lp != NULL)
- {
- if ((*lp)->l_idx != IDX_STILL_USED)
- {
- assert ((*lp)->l_idx >= 0 && (*lp)->l_idx < nloaded);
-
- if (!used[(*lp)->l_idx])
- {
- used[(*lp)->l_idx] = 1;
- /* If we marked a new object as used, and we've
- already processed it, then we need to go back
- and process again from that point forward to
- ensure we keep all of its dependencies also. */
- if ((*lp)->l_idx - 1 < done_index)
- done_index = (*lp)->l_idx - 1;
- }
- }
-
- ++lp;
- }
- }
- /* And the same for relocation dependencies. */
- if (l->l_reldeps != NULL)
- for (unsigned int j = 0; j < l->l_reldeps->act; ++j)
- {
- struct link_map *jmap = l->l_reldeps->list[j];
-
- if (jmap->l_idx != IDX_STILL_USED)
- {
- assert (jmap->l_idx >= 0 && jmap->l_idx < nloaded);
-
- if (!used[jmap->l_idx])
- {
- used[jmap->l_idx] = 1;
- if (jmap->l_idx - 1 < done_index)
- done_index = jmap->l_idx - 1;
- }
- }
- }
- }
-
- /* Sort the entries. */
- _dl_sort_fini (maps, nloaded, used, nsid);
-
- /* Call all termination functions at once. */
-#ifdef SHARED
- bool do_audit = GLRO(dl_naudit) > 0 && !ns->_ns_loaded->l_auditing;
-#endif
- bool unload_any = false;
- bool scope_mem_left = false;
- unsigned int unload_global = 0;
- unsigned int first_loaded = ~0;
- for (unsigned int i = 0; i < nloaded; ++i)
- {
- struct link_map *imap = maps[i];
-
- /* All elements must be in the same namespace. */
- assert (imap->l_ns == nsid);
-
- if (!used[i])
- {
- assert (imap->l_type == lt_loaded
- && (imap->l_flags_1 & DF_1_NODELETE) == 0);
-
- /* Call its termination function. Do not do it for
- half-cooked objects. */
- if (imap->l_init_called)
- {
- /* When debugging print a message first. */
- if (__builtin_expect (GLRO(dl_debug_mask) & DL_DEBUG_IMPCALLS,
- 0))
- _dl_debug_printf ("\ncalling fini: %s [%lu]\n\n",
- imap->l_name, nsid);
-
- if (imap->l_info[DT_FINI_ARRAY] != NULL)
- {
- ElfW(Addr) *array =
- (ElfW(Addr) *) (imap->l_addr
- + imap->l_info[DT_FINI_ARRAY]->d_un.d_ptr);
- unsigned int sz = (imap->l_info[DT_FINI_ARRAYSZ]->d_un.d_val
- / sizeof (ElfW(Addr)));
-
- while (sz-- > 0)
- ((fini_t) array[sz]) ();
- }
-
- /* Next try the old-style destructor. */
- if (imap->l_info[DT_FINI] != NULL)
- DL_CALL_DT_FINI (imap, ((void *) imap->l_addr
- + imap->l_info[DT_FINI]->d_un.d_ptr));
- }
-
-#ifdef SHARED
- /* Auditing checkpoint: we remove an object. */
- if (__glibc_unlikely (do_audit))
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objclose != NULL)
- /* Return value is ignored. */
- (void) afct->objclose (&imap->l_audit[cnt].cookie);
-
- afct = afct->next;
- }
- }
-#endif
-
- /* This object must not be used anymore. */
- imap->l_removed = 1;
-
- /* We indeed have an object to remove. */
- unload_any = true;
-
- if (imap->l_global)
- ++unload_global;
-
- /* Remember where the first dynamically loaded object is. */
- if (i < first_loaded)
- first_loaded = i;
- }
- /* Else used[i]. */
- else if (imap->l_type == lt_loaded)
- {
- struct r_scope_elem *new_list = NULL;
-
- if (imap->l_searchlist.r_list == NULL && imap->l_initfini != NULL)
- {
- /* The object is still used. But one of the objects we are
- unloading right now is responsible for loading it. If
- the current object does not have it's own scope yet we
- have to create one. This has to be done before running
- the finalizers.
-
- To do this count the number of dependencies. */
- unsigned int cnt;
- for (cnt = 1; imap->l_initfini[cnt] != NULL; ++cnt)
- ;
-
- /* We simply reuse the l_initfini list. */
- imap->l_searchlist.r_list = &imap->l_initfini[cnt + 1];
- imap->l_searchlist.r_nlist = cnt;
-
- new_list = &imap->l_searchlist;
- }
-
- /* Count the number of scopes which remain after the unload.
- When we add the local search list count it. Always add
- one for the terminating NULL pointer. */
- size_t remain = (new_list != NULL) + 1;
- bool removed_any = false;
- for (size_t cnt = 0; imap->l_scope[cnt] != NULL; ++cnt)
- /* This relies on l_scope[] entries being always set either
- to its own l_symbolic_searchlist address, or some map's
- l_searchlist address. */
- if (imap->l_scope[cnt] != &imap->l_symbolic_searchlist)
- {
- struct link_map *tmap = (struct link_map *)
- ((char *) imap->l_scope[cnt]
- - offsetof (struct link_map, l_searchlist));
- assert (tmap->l_ns == nsid);
- if (tmap->l_idx == IDX_STILL_USED)
- ++remain;
- else
- removed_any = true;
- }
- else
- ++remain;
-
- if (removed_any)
- {
- /* Always allocate a new array for the scope. This is
- necessary since we must be able to determine the last
- user of the current array. If possible use the link map's
- memory. */
- size_t new_size;
- struct r_scope_elem **newp;
-
-#define SCOPE_ELEMS(imap) \
- (sizeof (imap->l_scope_mem) / sizeof (imap->l_scope_mem[0]))
-
- if (imap->l_scope != imap->l_scope_mem
- && remain < SCOPE_ELEMS (imap))
- {
- new_size = SCOPE_ELEMS (imap);
- newp = imap->l_scope_mem;
- }
- else
- {
- new_size = imap->l_scope_max;
- newp = (struct r_scope_elem **)
- malloc (new_size * sizeof (struct r_scope_elem *));
- if (newp == NULL)
- _dl_signal_error (ENOMEM, "dlclose", NULL,
- N_("cannot create scope list"));
- }
-
- /* Copy over the remaining scope elements. */
- remain = 0;
- for (size_t cnt = 0; imap->l_scope[cnt] != NULL; ++cnt)
- {
- if (imap->l_scope[cnt] != &imap->l_symbolic_searchlist)
- {
- struct link_map *tmap = (struct link_map *)
- ((char *) imap->l_scope[cnt]
- - offsetof (struct link_map, l_searchlist));
- if (tmap->l_idx != IDX_STILL_USED)
- {
- /* Remove the scope. Or replace with own map's
- scope. */
- if (new_list != NULL)
- {
- newp[remain++] = new_list;
- new_list = NULL;
- }
- continue;
- }
- }
-
- newp[remain++] = imap->l_scope[cnt];
- }
- newp[remain] = NULL;
-
- struct r_scope_elem **old = imap->l_scope;
-
- imap->l_scope = newp;
-
- /* No user anymore, we can free it now. */
- if (old != imap->l_scope_mem)
- {
- if (_dl_scope_free (old))
- /* If _dl_scope_free used THREAD_GSCOPE_WAIT (),
- no need to repeat it. */
- scope_mem_left = false;
- }
- else
- scope_mem_left = true;
-
- imap->l_scope_max = new_size;
- }
- else if (new_list != NULL)
- {
- /* We didn't change the scope array, so reset the search
- list. */
- imap->l_searchlist.r_list = NULL;
- imap->l_searchlist.r_nlist = 0;
- }
-
- /* The loader is gone, so mark the object as not having one.
- Note: l_idx != IDX_STILL_USED -> object will be removed. */
- if (imap->l_loader != NULL
- && imap->l_loader->l_idx != IDX_STILL_USED)
- imap->l_loader = NULL;
-
- /* Remember where the first dynamically loaded object is. */
- if (i < first_loaded)
- first_loaded = i;
- }
- }
-
- /* If there are no objects to unload, do nothing further. */
- if (!unload_any)
- goto out;
-
-#ifdef SHARED
- /* Auditing checkpoint: we will start deleting objects. */
- if (__glibc_unlikely (do_audit))
- {
- struct link_map *head = ns->_ns_loaded;
- struct audit_ifaces *afct = GLRO(dl_audit);
- /* Do not call the functions for any auditing object. */
- if (head->l_auditing == 0)
- {
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&head->l_audit[cnt].cookie, LA_ACT_DELETE);
-
- afct = afct->next;
- }
- }
- }
-#endif
-
- /* Notify the debugger we are about to remove some loaded objects. */
- struct r_debug *r = _dl_debug_initialize (0, nsid);
- r->r_state = RT_DELETE;
- _dl_debug_state ();
- LIBC_PROBE (unmap_start, 2, nsid, r);
-
- if (unload_global)
- {
- /* Some objects are in the global scope list. Remove them. */
- struct r_scope_elem *ns_msl = ns->_ns_main_searchlist;
- unsigned int i;
- unsigned int j = 0;
- unsigned int cnt = ns_msl->r_nlist;
-
- while (cnt > 0 && ns_msl->r_list[cnt - 1]->l_removed)
- --cnt;
-
- if (cnt + unload_global == ns_msl->r_nlist)
- /* Speed up removing most recently added objects. */
- j = cnt;
- else
- for (i = 0; i < cnt; i++)
- if (ns_msl->r_list[i]->l_removed == 0)
- {
- if (i != j)
- ns_msl->r_list[j] = ns_msl->r_list[i];
- j++;
- }
- ns_msl->r_nlist = j;
- }
-
- if (!RTLD_SINGLE_THREAD_P
- && (unload_global
- || scope_mem_left
- || (GL(dl_scope_free_list) != NULL
- && GL(dl_scope_free_list)->count)))
- {
- THREAD_GSCOPE_WAIT ();
-
- /* Now we can free any queued old scopes. */
- struct dl_scope_free_list *fsl = GL(dl_scope_free_list);
- if (fsl != NULL)
- while (fsl->count > 0)
- free (fsl->list[--fsl->count]);
- }
-
- size_t tls_free_start;
- size_t tls_free_end;
- tls_free_start = tls_free_end = NO_TLS_OFFSET;
-
- /* We modify the list of loaded objects. */
- __rtld_lock_lock_recursive (GL(dl_load_write_lock));
-
- /* Check each element of the search list to see if all references to
- it are gone. */
- for (unsigned int i = first_loaded; i < nloaded; ++i)
- {
- struct link_map *imap = maps[i];
- if (!used[i])
- {
- assert (imap->l_type == lt_loaded);
-
- /* That was the last reference, and this was a dlopen-loaded
- object. We can unmap it. */
-
- /* Remove the object from the dtv slotinfo array if it uses TLS. */
- if (__glibc_unlikely (imap->l_tls_blocksize > 0))
- {
- any_tls = true;
-
- if (GL(dl_tls_dtv_slotinfo_list) != NULL
- && ! remove_slotinfo (imap->l_tls_modid,
- GL(dl_tls_dtv_slotinfo_list), 0,
- imap->l_init_called))
- /* All dynamically loaded modules with TLS are unloaded. */
- GL(dl_tls_max_dtv_idx) = GL(dl_tls_static_nelem);
-
- if (imap->l_tls_offset != NO_TLS_OFFSET
- && imap->l_tls_offset != FORCED_DYNAMIC_TLS_OFFSET)
- {
- /* Collect a contiguous chunk built from the objects in
- this search list, going in either direction. When the
- whole chunk is at the end of the used area then we can
- reclaim it. */
-#if TLS_TCB_AT_TP
- if (tls_free_start == NO_TLS_OFFSET
- || (size_t) imap->l_tls_offset == tls_free_start)
- {
- /* Extend the contiguous chunk being reclaimed. */
- tls_free_start
- = imap->l_tls_offset - imap->l_tls_blocksize;
-
- if (tls_free_end == NO_TLS_OFFSET)
- tls_free_end = imap->l_tls_offset;
- }
- else if (imap->l_tls_offset - imap->l_tls_blocksize
- == tls_free_end)
- /* Extend the chunk backwards. */
- tls_free_end = imap->l_tls_offset;
- else
- {
- /* This isn't contiguous with the last chunk freed.
- One of them will be leaked unless we can free
- one block right away. */
- if (tls_free_end == GL(dl_tls_static_used))
- {
- GL(dl_tls_static_used) = tls_free_start;
- tls_free_end = imap->l_tls_offset;
- tls_free_start
- = tls_free_end - imap->l_tls_blocksize;
- }
- else if ((size_t) imap->l_tls_offset
- == GL(dl_tls_static_used))
- GL(dl_tls_static_used)
- = imap->l_tls_offset - imap->l_tls_blocksize;
- else if (tls_free_end < (size_t) imap->l_tls_offset)
- {
- /* We pick the later block. It has a chance to
- be freed. */
- tls_free_end = imap->l_tls_offset;
- tls_free_start
- = tls_free_end - imap->l_tls_blocksize;
- }
- }
-#elif TLS_DTV_AT_TP
- if (tls_free_start == NO_TLS_OFFSET)
- {
- tls_free_start = imap->l_tls_firstbyte_offset;
- tls_free_end = (imap->l_tls_offset
- + imap->l_tls_blocksize);
- }
- else if (imap->l_tls_firstbyte_offset == tls_free_end)
- /* Extend the contiguous chunk being reclaimed. */
- tls_free_end = imap->l_tls_offset + imap->l_tls_blocksize;
- else if (imap->l_tls_offset + imap->l_tls_blocksize
- == tls_free_start)
- /* Extend the chunk backwards. */
- tls_free_start = imap->l_tls_firstbyte_offset;
- /* This isn't contiguous with the last chunk freed.
- One of them will be leaked unless we can free
- one block right away. */
- else if (imap->l_tls_offset + imap->l_tls_blocksize
- == GL(dl_tls_static_used))
- GL(dl_tls_static_used) = imap->l_tls_firstbyte_offset;
- else if (tls_free_end == GL(dl_tls_static_used))
- {
- GL(dl_tls_static_used) = tls_free_start;
- tls_free_start = imap->l_tls_firstbyte_offset;
- tls_free_end = imap->l_tls_offset + imap->l_tls_blocksize;
- }
- else if (tls_free_end < imap->l_tls_firstbyte_offset)
- {
- /* We pick the later block. It has a chance to
- be freed. */
- tls_free_start = imap->l_tls_firstbyte_offset;
- tls_free_end = imap->l_tls_offset + imap->l_tls_blocksize;
- }
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
- }
- }
-
- /* Reset unique symbols if forced. */
- if (force)
- {
- struct unique_sym_table *tab = &ns->_ns_unique_sym_table;
- __rtld_lock_lock_recursive (tab->lock);
- struct unique_sym *entries = tab->entries;
- if (entries != NULL)
- {
- size_t idx, size = tab->size;
- for (idx = 0; idx < size; ++idx)
- {
- /* Clear unique symbol entries that belong to this
- object. */
- if (entries[idx].name != NULL
- && entries[idx].map == imap)
- {
- entries[idx].name = NULL;
- entries[idx].hashval = 0;
- tab->n_elements--;
- }
- }
- }
- __rtld_lock_unlock_recursive (tab->lock);
- }
-
- /* We can unmap all the maps at once. We determined the
- start address and length when we loaded the object and
- the `munmap' call does the rest. */
- DL_UNMAP (imap);
-
- /* Finally, unlink the data structure and free it. */
-#if DL_NNS == 1
- /* The assert in the (imap->l_prev == NULL) case gives
- the compiler license to warn that NS points outside
- the dl_ns array bounds in that case (as nsid != LM_ID_BASE
- is tantamount to nsid >= DL_NNS). That should be impossible
- in this configuration, so just assert about it instead. */
- assert (nsid == LM_ID_BASE);
- assert (imap->l_prev != NULL);
-#else
- if (imap->l_prev == NULL)
- {
- assert (nsid != LM_ID_BASE);
- ns->_ns_loaded = imap->l_next;
-
- /* Update the pointer to the head of the list
- we leave for debuggers to examine. */
- r->r_map = (void *) ns->_ns_loaded;
- }
- else
-#endif
- imap->l_prev->l_next = imap->l_next;
-
- --ns->_ns_nloaded;
- if (imap->l_next != NULL)
- imap->l_next->l_prev = imap->l_prev;
-
- free (imap->l_versions);
- if (imap->l_origin != (char *) -1)
- free ((char *) imap->l_origin);
-
- free (imap->l_reldeps);
-
- /* Print debugging message. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("\nfile=%s [%lu]; destroying link map\n",
- imap->l_name, imap->l_ns);
-
- /* This name always is allocated. */
- free (imap->l_name);
- /* Remove the list with all the names of the shared object. */
-
- struct libname_list *lnp = imap->l_libname;
- do
- {
- struct libname_list *this = lnp;
- lnp = lnp->next;
- if (!this->dont_free)
- free (this);
- }
- while (lnp != NULL);
-
- /* Remove the searchlists. */
- free (imap->l_initfini);
-
- /* Remove the scope array if we allocated it. */
- if (imap->l_scope != imap->l_scope_mem)
- free (imap->l_scope);
-
- if (imap->l_phdr_allocated)
- free ((void *) imap->l_phdr);
-
- if (imap->l_rpath_dirs.dirs != (void *) -1)
- free (imap->l_rpath_dirs.dirs);
- if (imap->l_runpath_dirs.dirs != (void *) -1)
- free (imap->l_runpath_dirs.dirs);
-
- free (imap);
- }
- }
-
- __rtld_lock_unlock_recursive (GL(dl_load_write_lock));
-
- /* If we removed any object which uses TLS bump the generation counter. */
- if (any_tls)
- {
- if (__glibc_unlikely (++GL(dl_tls_generation) == 0))
- _dl_fatal_printf ("TLS generation counter wrapped! Please report as described in "REPORT_BUGS_TO".\n");
-
- if (tls_free_end == GL(dl_tls_static_used))
- GL(dl_tls_static_used) = tls_free_start;
- }
-
-#ifdef SHARED
- /* Auditing checkpoint: we have deleted all objects. */
- if (__glibc_unlikely (do_audit))
- {
- struct link_map *head = ns->_ns_loaded;
- /* Do not call the functions for any auditing object. */
- if (head->l_auditing == 0)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&head->l_audit[cnt].cookie, LA_ACT_CONSISTENT);
-
- afct = afct->next;
- }
- }
- }
-#endif
-
- if (__builtin_expect (ns->_ns_loaded == NULL, 0)
- && nsid == GL(dl_nns) - 1)
- do
- --GL(dl_nns);
- while (GL(dl_ns)[GL(dl_nns) - 1]._ns_loaded == NULL);
-
- /* Notify the debugger those objects are finalized and gone. */
- r->r_state = RT_CONSISTENT;
- _dl_debug_state ();
- LIBC_PROBE (unmap_complete, 2, nsid, r);
-
- /* Recheck if we need to retry, release the lock. */
- out:
- if (dl_close_state == rerun)
- goto retry;
-
- dl_close_state = not_pending;
-}
-
-
-void
-_dl_close (void *_map)
-{
- struct link_map *map = _map;
-
- /* We must take the lock to examine the contents of map and avoid
- concurrent dlopens. */
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- /* At this point we are guaranteed nobody else is touching the list of
- loaded maps, but a concurrent dlclose might have freed our map
- before we took the lock. There is no way to detect this (see below)
- so we proceed assuming this isn't the case. First see whether we
- can remove the object at all. */
- if (__glibc_unlikely (map->l_flags_1 & DF_1_NODELETE))
- {
- /* Nope. Do nothing. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return;
- }
-
- /* At present this is an unreliable check except in the case where the
- caller has recursively called dlclose and we are sure the link map
- has not been freed. In a non-recursive dlclose the map itself
- might have been freed and this access is potentially a data race
- with whatever other use this memory might have now, or worse we
- might silently corrupt memory if it looks enough like a link map.
- POSIX has language in dlclose that appears to guarantee that this
- should be a detectable case and given that dlclose should be threadsafe
- we need this to be a reliable detection.
- This is bug 20990. */
- if (__builtin_expect (map->l_direct_opencount, 1) == 0)
- {
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- _dl_signal_error (0, map->l_name, NULL, N_("shared object not open"));
- }
-
- _dl_close_worker (map, false);
-
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-}
diff --git a/elf/dl-conflict.c b/elf/dl-conflict.c
deleted file mode 100644
index 3cbd07435e..0000000000
--- a/elf/dl-conflict.c
+++ /dev/null
@@ -1,74 +0,0 @@
-/* Resolve conflicts against already prelinked libraries.
- Copyright (C) 2001-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2001.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public License as
- published by the Free Software Foundation; either version 2.1 of the
- License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; see the file COPYING.LIB. If
- not, see <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/types.h>
-#include "dynamic-link.h"
-
-void
-_dl_resolve_conflicts (struct link_map *l, ElfW(Rela) *conflict,
- ElfW(Rela) *conflictend)
-{
-#if ! ELF_MACHINE_NO_RELA
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_RELOC))
- _dl_debug_printf ("\nconflict processing: %s\n", DSO_FILENAME (l->l_name));
-
- {
- /* Do the conflict relocation of the object and library GOT and other
- data. */
-
- /* This macro is used as a callback from the ELF_DYNAMIC_RELOCATE code. */
-#define RESOLVE_MAP(ref, version, flags) (*ref = NULL, NULL)
-#define RESOLVE(ref, version, flags) (*ref = NULL, 0)
-#define RESOLVE_CONFLICT_FIND_MAP(map, r_offset) \
- do { \
- while ((resolve_conflict_map->l_map_end < (ElfW(Addr)) (r_offset)) \
- || (resolve_conflict_map->l_map_start > (ElfW(Addr)) (r_offset))) \
- resolve_conflict_map = resolve_conflict_map->l_next; \
- \
- (map) = resolve_conflict_map; \
- } while (0)
-
- /* Prelinking makes no sense for anything but the main namespace. */
- assert (l->l_ns == LM_ID_BASE);
- struct link_map *resolve_conflict_map __attribute__ ((__unused__))
- = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
-
-#include "dynamic-link.h"
-
- /* Override these, defined in dynamic-link.h. */
-#undef CHECK_STATIC_TLS
-#define CHECK_STATIC_TLS(ref_map, sym_map) ((void) 0)
-#undef TRY_STATIC_TLS
-#define TRY_STATIC_TLS(ref_map, sym_map) (0)
-
- GL(dl_num_cache_relocations) += conflictend - conflict;
-
- for (; conflict < conflictend; ++conflict)
- elf_machine_rela (l, conflict, NULL, NULL, (void *) conflict->r_offset,
- 0);
- }
-#endif
-}
diff --git a/elf/dl-debug.c b/elf/dl-debug.c
deleted file mode 100644
index f3957044f6..0000000000
--- a/elf/dl-debug.c
+++ /dev/null
@@ -1,76 +0,0 @@
-/* Communicate dynamic linker state to the debugger at runtime.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <ldsodefs.h>
-
-
-/* These are the members in the public `struct link_map' type.
- Sanity check that the internal type and the public type match. */
-#define VERIFY_MEMBER(name) \
- (offsetof (struct link_map_public, name) == offsetof (struct link_map, name))
-extern const int verify_link_map_members[(VERIFY_MEMBER (l_addr)
- && VERIFY_MEMBER (l_name)
- && VERIFY_MEMBER (l_ld)
- && VERIFY_MEMBER (l_next)
- && VERIFY_MEMBER (l_prev))
- ? 1 : -1];
-
-/* This structure communicates dl state to the debugger. The debugger
- normally finds it via the DT_DEBUG entry in the dynamic section, but in
- a statically-linked program there is no dynamic section for the debugger
- to examine and it looks for this particular symbol name. */
-struct r_debug _r_debug;
-
-
-/* Initialize _r_debug if it has not already been done. The argument is
- the run-time load address of the dynamic linker, to be put in
- _r_debug.r_ldbase. Returns the address of _r_debug. */
-
-struct r_debug *
-internal_function
-_dl_debug_initialize (ElfW(Addr) ldbase, Lmid_t ns)
-{
- struct r_debug *r;
-
- if (ns == LM_ID_BASE)
- r = &_r_debug;
- else
- r = &GL(dl_ns)[ns]._ns_debug;
-
- if (r->r_map == NULL || ldbase != 0)
- {
- /* Tell the debugger where to find the map of loaded objects. */
- r->r_version = 1 /* R_DEBUG_VERSION XXX */;
- r->r_ldbase = ldbase ?: _r_debug.r_ldbase;
- r->r_map = (void *) GL(dl_ns)[ns]._ns_loaded;
- r->r_brk = (ElfW(Addr)) &_dl_debug_state;
- }
-
- return r;
-}
-
-
-/* This function exists solely to have a breakpoint set on it by the
- debugger. The debugger is supposed to find this function's address by
- examining the r_brk member of struct r_debug, but GDB 4.15 in fact looks
- for this particular symbol name in the PT_INTERP file. */
-void
-_dl_debug_state (void)
-{
-}
-rtld_hidden_def (_dl_debug_state)
diff --git a/elf/dl-deps.c b/elf/dl-deps.c
deleted file mode 100644
index 1b8bac6593..0000000000
--- a/elf/dl-deps.c
+++ /dev/null
@@ -1,688 +0,0 @@
-/* Load the dependencies of a mapped object.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <atomic.h>
-#include <assert.h>
-#include <dlfcn.h>
-#include <errno.h>
-#include <libintl.h>
-#include <stddef.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/param.h>
-#include <ldsodefs.h>
-
-#include <dl-dst.h>
-
-/* Whether an shared object references one or more auxiliary objects
- is signaled by the AUXTAG entry in l_info. */
-#define AUXTAG (DT_NUM + DT_THISPROCNUM + DT_VERSIONTAGNUM \
- + DT_EXTRATAGIDX (DT_AUXILIARY))
-/* Whether an shared object references one or more auxiliary objects
- is signaled by the AUXTAG entry in l_info. */
-#define FILTERTAG (DT_NUM + DT_THISPROCNUM + DT_VERSIONTAGNUM \
- + DT_EXTRATAGIDX (DT_FILTER))
-
-
-/* When loading auxiliary objects we must ignore errors. It's ok if
- an object is missing. */
-struct openaux_args
- {
- /* The arguments to openaux. */
- struct link_map *map;
- int trace_mode;
- int open_mode;
- const char *strtab;
- const char *name;
-
- /* The return value of openaux. */
- struct link_map *aux;
- };
-
-static void
-openaux (void *a)
-{
- struct openaux_args *args = (struct openaux_args *) a;
-
- args->aux = _dl_map_object (args->map, args->name,
- (args->map->l_type == lt_executable
- ? lt_library : args->map->l_type),
- args->trace_mode, args->open_mode,
- args->map->l_ns);
-}
-
-static ptrdiff_t
-internal_function
-_dl_build_local_scope (struct link_map **list, struct link_map *map)
-{
- struct link_map **p = list;
- struct link_map **q;
-
- *p++ = map;
- map->l_reserved = 1;
- if (map->l_initfini)
- for (q = map->l_initfini + 1; *q; ++q)
- if (! (*q)->l_reserved)
- p += _dl_build_local_scope (p, *q);
- return p - list;
-}
-
-
-/* We use a very special kind of list to track the path
- through the list of loaded shared objects. We have to
- produce a flat list with unique members of all involved objects.
-*/
-struct list
- {
- int done; /* Nonzero if this map was processed. */
- struct link_map *map; /* The data. */
- struct list *next; /* Elements for normal list. */
- };
-
-
-/* Macro to expand DST. It is an macro since we use `alloca'. */
-#define expand_dst(l, str, fatal) \
- ({ \
- const char *__str = (str); \
- const char *__result = __str; \
- size_t __dst_cnt = DL_DST_COUNT (__str, 0); \
- \
- if (__dst_cnt != 0) \
- { \
- char *__newp; \
- \
- /* DST must not appear in SUID/SGID programs. */ \
- if (__libc_enable_secure) \
- _dl_signal_error (0, __str, NULL, N_("\
-DST not allowed in SUID/SGID programs")); \
- \
- __newp = (char *) alloca (DL_DST_REQUIRED (l, __str, strlen (__str), \
- __dst_cnt)); \
- \
- __result = _dl_dst_substitute (l, __str, __newp, 0); \
- \
- if (*__result == '\0') \
- { \
- /* The replacement for the DST is not known. We can't \
- processed. */ \
- if (fatal) \
- _dl_signal_error (0, __str, NULL, N_("\
-empty dynamic string token substitution")); \
- else \
- { \
- /* This is for DT_AUXILIARY. */ \
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS)) \
- _dl_debug_printf (N_("\
-cannot load auxiliary `%s' because of empty dynamic string token " \
- "substitution\n"), __str); \
- continue; \
- } \
- } \
- } \
- \
- __result; })
-
-static void
-preload (struct list *known, unsigned int *nlist, struct link_map *map)
-{
- known[*nlist].done = 0;
- known[*nlist].map = map;
- known[*nlist].next = &known[*nlist + 1];
-
- ++*nlist;
- /* We use `l_reserved' as a mark bit to detect objects we have
- already put in the search list and avoid adding duplicate
- elements later in the list. */
- map->l_reserved = 1;
-}
-
-void
-internal_function
-_dl_map_object_deps (struct link_map *map,
- struct link_map **preloads, unsigned int npreloads,
- int trace_mode, int open_mode)
-{
- struct list *known = __alloca (sizeof *known * (1 + npreloads + 1));
- struct list *runp, *tail;
- unsigned int nlist, i;
- /* Object name. */
- const char *name;
- int errno_saved;
- int errno_reason;
- const char *errstring;
- const char *objname;
-
- /* No loaded object so far. */
- nlist = 0;
-
- /* First load MAP itself. */
- preload (known, &nlist, map);
-
- /* Add the preloaded items after MAP but before any of its dependencies. */
- for (i = 0; i < npreloads; ++i)
- preload (known, &nlist, preloads[i]);
-
- /* Terminate the lists. */
- known[nlist - 1].next = NULL;
-
- /* Pointer to last unique object. */
- tail = &known[nlist - 1];
-
- /* No alloca'd space yet. */
- struct link_map **needed_space = NULL;
- size_t needed_space_bytes = 0;
-
- /* Process each element of the search list, loading each of its
- auxiliary objects and immediate dependencies. Auxiliary objects
- will be added in the list before the object itself and
- dependencies will be appended to the list as we step through it.
- This produces a flat, ordered list that represents a
- breadth-first search of the dependency tree.
-
- The whole process is complicated by the fact that we better
- should use alloca for the temporary list elements. But using
- alloca means we cannot use recursive function calls. */
- errno_saved = errno;
- errno_reason = 0;
- errstring = NULL;
- errno = 0;
- name = NULL;
- for (runp = known; runp; )
- {
- struct link_map *l = runp->map;
- struct link_map **needed = NULL;
- unsigned int nneeded = 0;
-
- /* Unless otherwise stated, this object is handled. */
- runp->done = 1;
-
- /* Allocate a temporary record to contain the references to the
- dependencies of this object. */
- if (l->l_searchlist.r_list == NULL && l->l_initfini == NULL
- && l != map && l->l_ldnum > 0)
- {
- size_t new_size = l->l_ldnum * sizeof (struct link_map *);
-
- if (new_size > needed_space_bytes)
- needed_space
- = extend_alloca (needed_space, needed_space_bytes, new_size);
-
- needed = needed_space;
- }
-
- if (l->l_info[DT_NEEDED] || l->l_info[AUXTAG] || l->l_info[FILTERTAG])
- {
- const char *strtab = (const void *) D_PTR (l, l_info[DT_STRTAB]);
- struct openaux_args args;
- struct list *orig;
- const ElfW(Dyn) *d;
-
- args.strtab = strtab;
- args.map = l;
- args.trace_mode = trace_mode;
- args.open_mode = open_mode;
- orig = runp;
-
- for (d = l->l_ld; d->d_tag != DT_NULL; ++d)
- if (__builtin_expect (d->d_tag, DT_NEEDED) == DT_NEEDED)
- {
- /* Map in the needed object. */
- struct link_map *dep;
-
- /* Recognize DSTs. */
- name = expand_dst (l, strtab + d->d_un.d_val, 0);
- /* Store the tag in the argument structure. */
- args.name = name;
-
- bool malloced;
- int err = _dl_catch_error (&objname, &errstring, &malloced,
- openaux, &args);
- if (__glibc_unlikely (errstring != NULL))
- {
- char *new_errstring = strdupa (errstring);
- objname = strdupa (objname);
- if (malloced)
- free ((char *) errstring);
- errstring = new_errstring;
-
- if (err)
- errno_reason = err;
- else
- errno_reason = -1;
- goto out;
- }
- else
- dep = args.aux;
-
- if (! dep->l_reserved)
- {
- /* Allocate new entry. */
- struct list *newp;
-
- newp = alloca (sizeof (struct list));
-
- /* Append DEP to the list. */
- newp->map = dep;
- newp->done = 0;
- newp->next = NULL;
- tail->next = newp;
- tail = newp;
- ++nlist;
- /* Set the mark bit that says it's already in the list. */
- dep->l_reserved = 1;
- }
-
- /* Remember this dependency. */
- if (needed != NULL)
- needed[nneeded++] = dep;
- }
- else if (d->d_tag == DT_AUXILIARY || d->d_tag == DT_FILTER)
- {
- struct list *newp;
-
- /* Recognize DSTs. */
- name = expand_dst (l, strtab + d->d_un.d_val,
- d->d_tag == DT_AUXILIARY);
- /* Store the tag in the argument structure. */
- args.name = name;
-
- /* Say that we are about to load an auxiliary library. */
- if (__builtin_expect (GLRO(dl_debug_mask) & DL_DEBUG_LIBS,
- 0))
- _dl_debug_printf ("load auxiliary object=%s"
- " requested by file=%s\n",
- name,
- DSO_FILENAME (l->l_name));
-
- /* We must be prepared that the addressed shared
- object is not available. For filter objects the dependency
- must be available. */
- bool malloced;
- int err = _dl_catch_error (&objname, &errstring, &malloced,
- openaux, &args);
-
- if (__glibc_unlikely (errstring != NULL))
- {
- if (d->d_tag == DT_AUXILIARY)
- {
- /* We are not interested in the error message. */
- assert (errstring != NULL);
- if (malloced)
- free ((char *) errstring);
-
- /* Simply ignore this error and continue the work. */
- continue;
- }
- else
- {
-
- char *new_errstring = strdupa (errstring);
- objname = strdupa (objname);
- if (malloced)
- free ((char *) errstring);
- errstring = new_errstring;
-
- if (err)
- errno_reason = err;
- else
- errno_reason = -1;
- goto out;
- }
- }
-
- /* The auxiliary object is actually available.
- Incorporate the map in all the lists. */
-
- /* Allocate new entry. This always has to be done. */
- newp = alloca (sizeof (struct list));
-
- /* We want to insert the new map before the current one,
- but we have no back links. So we copy the contents of
- the current entry over. Note that ORIG and NEWP now
- have switched their meanings. */
- memcpy (newp, orig, sizeof (*newp));
-
- /* Initialize new entry. */
- orig->done = 0;
- orig->map = args.aux;
-
- /* Remember this dependency. */
- if (needed != NULL)
- needed[nneeded++] = args.aux;
-
- /* We must handle two situations here: the map is new,
- so we must add it in all three lists. If the map
- is already known, we have two further possibilities:
- - if the object is before the current map in the
- search list, we do nothing. It is already found
- early
- - if the object is after the current one, we must
- move it just before the current map to make sure
- the symbols are found early enough
- */
- if (args.aux->l_reserved)
- {
- /* The object is already somewhere in the list.
- Locate it first. */
- struct list *late;
-
- /* This object is already in the search list we
- are building. Don't add a duplicate pointer.
- Just added by _dl_map_object. */
- for (late = newp; late->next != NULL; late = late->next)
- if (late->next->map == args.aux)
- break;
-
- if (late->next != NULL)
- {
- /* The object is somewhere behind the current
- position in the search path. We have to
- move it to this earlier position. */
- orig->next = newp;
-
- /* Now remove the later entry from the list
- and adjust the tail pointer. */
- if (tail == late->next)
- tail = late;
- late->next = late->next->next;
-
- /* We must move the object earlier in the chain. */
- if (args.aux->l_prev != NULL)
- args.aux->l_prev->l_next = args.aux->l_next;
- if (args.aux->l_next != NULL)
- args.aux->l_next->l_prev = args.aux->l_prev;
-
- args.aux->l_prev = newp->map->l_prev;
- newp->map->l_prev = args.aux;
- if (args.aux->l_prev != NULL)
- args.aux->l_prev->l_next = args.aux;
- args.aux->l_next = newp->map;
- }
- else
- {
- /* The object must be somewhere earlier in the
- list. Undo to the current list element what
- we did above. */
- memcpy (orig, newp, sizeof (*newp));
- continue;
- }
- }
- else
- {
- /* This is easy. We just add the symbol right here. */
- orig->next = newp;
- ++nlist;
- /* Set the mark bit that says it's already in the list. */
- args.aux->l_reserved = 1;
-
- /* The only problem is that in the double linked
- list of all objects we don't have this new
- object at the correct place. Correct this here. */
- if (args.aux->l_prev)
- args.aux->l_prev->l_next = args.aux->l_next;
- if (args.aux->l_next)
- args.aux->l_next->l_prev = args.aux->l_prev;
-
- args.aux->l_prev = newp->map->l_prev;
- newp->map->l_prev = args.aux;
- if (args.aux->l_prev != NULL)
- args.aux->l_prev->l_next = args.aux;
- args.aux->l_next = newp->map;
- }
-
- /* Move the tail pointer if necessary. */
- if (orig == tail)
- tail = newp;
-
- /* Move on the insert point. */
- orig = newp;
- }
- }
-
- /* Terminate the list of dependencies and store the array address. */
- if (needed != NULL)
- {
- needed[nneeded++] = NULL;
-
- struct link_map **l_initfini = (struct link_map **)
- malloc ((2 * nneeded + 1) * sizeof needed[0]);
- if (l_initfini == NULL)
- _dl_signal_error (ENOMEM, map->l_name, NULL,
- N_("cannot allocate dependency list"));
- l_initfini[0] = l;
- memcpy (&l_initfini[1], needed, nneeded * sizeof needed[0]);
- memcpy (&l_initfini[nneeded + 1], l_initfini,
- nneeded * sizeof needed[0]);
- atomic_write_barrier ();
- l->l_initfini = l_initfini;
- l->l_free_initfini = 1;
- }
-
- /* If we have no auxiliary objects just go on to the next map. */
- if (runp->done)
- do
- runp = runp->next;
- while (runp != NULL && runp->done);
- }
-
- out:
- if (errno == 0 && errno_saved != 0)
- __set_errno (errno_saved);
-
- struct link_map **old_l_initfini = NULL;
- if (map->l_initfini != NULL && map->l_type == lt_loaded)
- {
- /* This object was previously loaded as a dependency and we have
- a separate l_initfini list. We don't need it anymore. */
- assert (map->l_searchlist.r_list == NULL);
- old_l_initfini = map->l_initfini;
- }
-
- /* Store the search list we built in the object. It will be used for
- searches in the scope of this object. */
- struct link_map **l_initfini =
- (struct link_map **) malloc ((2 * nlist + 1)
- * sizeof (struct link_map *));
- if (l_initfini == NULL)
- _dl_signal_error (ENOMEM, map->l_name, NULL,
- N_("cannot allocate symbol search list"));
-
-
- map->l_searchlist.r_list = &l_initfini[nlist + 1];
- map->l_searchlist.r_nlist = nlist;
-
- for (nlist = 0, runp = known; runp; runp = runp->next)
- {
- if (__builtin_expect (trace_mode, 0) && runp->map->l_faked)
- /* This can happen when we trace the loading. */
- --map->l_searchlist.r_nlist;
- else
- map->l_searchlist.r_list[nlist++] = runp->map;
-
- /* Now clear all the mark bits we set in the objects on the search list
- to avoid duplicates, so the next call starts fresh. */
- runp->map->l_reserved = 0;
- }
-
- if (__builtin_expect (GLRO(dl_debug_mask) & DL_DEBUG_PRELINK, 0) != 0
- && map == GL(dl_ns)[LM_ID_BASE]._ns_loaded)
- {
- /* If we are to compute conflicts, we have to build local scope
- for each library, not just the ultimate loader. */
- for (i = 0; i < nlist; ++i)
- {
- struct link_map *l = map->l_searchlist.r_list[i];
- unsigned int j, cnt;
-
- /* The local scope has been already computed. */
- if (l == map
- || (l->l_local_scope[0]
- && l->l_local_scope[0]->r_nlist) != 0)
- continue;
-
- if (l->l_info[AUXTAG] || l->l_info[FILTERTAG])
- {
- /* As current DT_AUXILIARY/DT_FILTER implementation needs to be
- rewritten, no need to bother with prelinking the old
- implementation. */
- _dl_signal_error (EINVAL, l->l_name, NULL, N_("\
-Filters not supported with LD_TRACE_PRELINKING"));
- }
-
- cnt = _dl_build_local_scope (l_initfini, l);
- assert (cnt <= nlist);
- for (j = 0; j < cnt; j++)
- {
- l_initfini[j]->l_reserved = 0;
- if (j && __builtin_expect (l_initfini[j]->l_info[DT_SYMBOLIC]
- != NULL, 0))
- l->l_symbolic_in_local_scope = true;
- }
-
- l->l_local_scope[0] =
- (struct r_scope_elem *) malloc (sizeof (struct r_scope_elem)
- + (cnt
- * sizeof (struct link_map *)));
- if (l->l_local_scope[0] == NULL)
- _dl_signal_error (ENOMEM, map->l_name, NULL,
- N_("cannot allocate symbol search list"));
- l->l_local_scope[0]->r_nlist = cnt;
- l->l_local_scope[0]->r_list =
- (struct link_map **) (l->l_local_scope[0] + 1);
- memcpy (l->l_local_scope[0]->r_list, l_initfini,
- cnt * sizeof (struct link_map *));
- }
- }
-
- /* Maybe we can remove some relocation dependencies now. */
- assert (map->l_searchlist.r_list[0] == map);
- struct link_map_reldeps *l_reldeps = NULL;
- if (map->l_reldeps != NULL)
- {
- for (i = 1; i < nlist; ++i)
- map->l_searchlist.r_list[i]->l_reserved = 1;
-
- struct link_map **list = &map->l_reldeps->list[0];
- for (i = 0; i < map->l_reldeps->act; ++i)
- if (list[i]->l_reserved)
- {
- /* Need to allocate new array of relocation dependencies. */
- l_reldeps = malloc (sizeof (*l_reldeps)
- + map->l_reldepsmax
- * sizeof (struct link_map *));
- if (l_reldeps == NULL)
- /* Bad luck, keep the reldeps duplicated between
- map->l_reldeps->list and map->l_initfini lists. */
- ;
- else
- {
- unsigned int j = i;
- memcpy (&l_reldeps->list[0], &list[0],
- i * sizeof (struct link_map *));
- for (i = i + 1; i < map->l_reldeps->act; ++i)
- if (!list[i]->l_reserved)
- l_reldeps->list[j++] = list[i];
- l_reldeps->act = j;
- }
- }
-
- for (i = 1; i < nlist; ++i)
- map->l_searchlist.r_list[i]->l_reserved = 0;
- }
-
- /* Sort the initializer list to take dependencies into account. The binary
- itself will always be initialize last. */
- memcpy (l_initfini, map->l_searchlist.r_list,
- nlist * sizeof (struct link_map *));
- if (__glibc_likely (nlist > 1))
- {
- /* We can skip looking for the binary itself which is at the front
- of the search list. */
- i = 1;
- uint16_t seen[nlist];
- memset (seen, 0, nlist * sizeof (seen[0]));
- while (1)
- {
- /* Keep track of which object we looked at this round. */
- ++seen[i];
- struct link_map *thisp = l_initfini[i];
-
- /* Find the last object in the list for which the current one is
- a dependency and move the current object behind the object
- with the dependency. */
- unsigned int k = nlist - 1;
- while (k > i)
- {
- struct link_map **runp = l_initfini[k]->l_initfini;
- if (runp != NULL)
- /* Look through the dependencies of the object. */
- while (*runp != NULL)
- if (__glibc_unlikely (*runp++ == thisp))
- {
- /* Move the current object to the back past the last
- object with it as the dependency. */
- memmove (&l_initfini[i], &l_initfini[i + 1],
- (k - i) * sizeof (l_initfini[0]));
- l_initfini[k] = thisp;
-
- if (seen[i + 1] > nlist - i)
- {
- ++i;
- goto next_clear;
- }
-
- uint16_t this_seen = seen[i];
- memmove (&seen[i], &seen[i + 1],
- (k - i) * sizeof (seen[0]));
- seen[k] = this_seen;
-
- goto next;
- }
-
- --k;
- }
-
- if (++i == nlist)
- break;
- next_clear:
- memset (&seen[i], 0, (nlist - i) * sizeof (seen[0]));
-
- next:;
- }
- }
-
- /* Terminate the list of dependencies. */
- l_initfini[nlist] = NULL;
- atomic_write_barrier ();
- map->l_initfini = l_initfini;
- map->l_free_initfini = 1;
- if (l_reldeps != NULL)
- {
- atomic_write_barrier ();
- void *old_l_reldeps = map->l_reldeps;
- map->l_reldeps = l_reldeps;
- _dl_scope_free (old_l_reldeps);
- }
- if (old_l_initfini != NULL)
- _dl_scope_free (old_l_initfini);
-
- if (errno_reason)
- _dl_signal_error (errno_reason == -1 ? 0 : errno_reason, objname,
- NULL, errstring);
-}
diff --git a/elf/dl-dst.h b/elf/dl-dst.h
deleted file mode 100644
index a96513d4dc..0000000000
--- a/elf/dl-dst.h
+++ /dev/null
@@ -1,74 +0,0 @@
-/* Handling of dynamic sring tokens.
- Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "trusted-dirs.h"
-
-/* Determine the number of DST elements in the name. Only if IS_PATH is
- nonzero paths are recognized (i.e., multiple, ':' separated filenames). */
-#define DL_DST_COUNT(name, is_path) \
- ({ \
- size_t __cnt = 0; \
- const char *__sf = strchr (name, '$'); \
- \
- if (__glibc_unlikely (__sf != NULL)) \
- __cnt = _dl_dst_count (__sf, is_path); \
- \
- __cnt; })
-
-
-#ifdef SHARED
-# define IS_RTLD(l) (l) == &GL(dl_rtld_map)
-#else
-# define IS_RTLD(l) 0
-#endif
-/* Guess from the number of DSTs the length of the result string. */
-#define DL_DST_REQUIRED(l, name, len, cnt) \
- ({ \
- size_t __len = (len); \
- size_t __cnt = (cnt); \
- \
- if (__cnt > 0) \
- { \
- size_t dst_len; \
- /* Now we make a guess how many extra characters on top of the \
- length of S we need to represent the result. We know that \
- we have CNT replacements. Each at most can use \
- MAX (MAX (strlen (ORIGIN), strlen (_dl_platform)), \
- strlen (DL_DST_LIB)) \
- minus 4 (which is the length of "$LIB"). \
- \
- First get the origin string if it is not available yet. \
- This can only happen for the map of the executable or, when \
- auditing, in ld.so. */ \
- if ((l)->l_origin == NULL) \
- { \
- assert ((l)->l_name[0] == '\0' || IS_RTLD (l)); \
- (l)->l_origin = _dl_get_origin (); \
- dst_len = ((l)->l_origin && (l)->l_origin != (char *) -1 \
- ? strlen ((l)->l_origin) : 0); \
- } \
- else \
- dst_len = (l)->l_origin == (char *) -1 \
- ? 0 : strlen ((l)->l_origin); \
- dst_len = MAX (MAX (dst_len, GLRO(dl_platformlen)), \
- strlen (DL_DST_LIB)); \
- if (dst_len > 4) \
- __len += __cnt * (dst_len - 4); \
- } \
- \
- __len; })
diff --git a/elf/dl-environ.c b/elf/dl-environ.c
deleted file mode 100644
index cbffec8808..0000000000
--- a/elf/dl-environ.c
+++ /dev/null
@@ -1,85 +0,0 @@
-/* Environment handling for dynamic loader.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <string.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-
-/* Walk through the environment of the process and return all entries
- starting with `LD_'. */
-char *
-internal_function
-_dl_next_ld_env_entry (char ***position)
-{
- char **current = *position;
- char *result = NULL;
-
- while (*current != NULL)
- {
- if (__builtin_expect ((*current)[0] == 'L', 0)
- && (*current)[1] == 'D' && (*current)[2] == '_')
- {
- result = &(*current)[3];
-
- /* Save current position for next visit. */
- *position = ++current;
-
- break;
- }
-
- ++current;
- }
-
- return result;
-}
-
-
-/* In ld.so __environ is not exported. */
-extern char **__environ attribute_hidden;
-
-int
-unsetenv (const char *name)
-{
- char **ep;
-
- ep = __environ;
- while (*ep != NULL)
- {
- size_t cnt = 0;
-
- while ((*ep)[cnt] == name[cnt] && name[cnt] != '\0')
- ++cnt;
-
- if (name[cnt] == '\0' && (*ep)[cnt] == '=')
- {
- /* Found it. Remove this pointer by moving later ones to
- the front. */
- char **dp = ep;
-
- do
- dp[0] = dp[1];
- while (*dp++);
- /* Continue the loop in case NAME appears again. */
- }
- else
- ++ep;
- }
-
- return 0;
-}
diff --git a/elf/dl-error-minimal.c b/elf/dl-error-minimal.c
deleted file mode 100644
index 384c9b0edc..0000000000
--- a/elf/dl-error-minimal.c
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Error handling for runtime dynamic linker, minimal version.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This version does lives in ld.so, does not use thread-local data
- and supports _dl_signal_cerror and _dl_receive_error. */
-
-#define DL_ERROR_BOOTSTRAP 1
-#include "dl-error-skeleton.c"
diff --git a/elf/dl-error-skeleton.c b/elf/dl-error-skeleton.c
deleted file mode 100644
index 8e5888d4bd..0000000000
--- a/elf/dl-error-skeleton.c
+++ /dev/null
@@ -1,230 +0,0 @@
-/* Template for error handling for runtime dynamic linker.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* The following macro needs to be defined before including this
- skeleton file:
-
- DL_ERROR_BOOTSTRAP
-
- If 1, do not use TLS and implement _dl_signal_cerror and
- _dl_receive_error. If 0, TLS is used, and the variants with
- error callbacks are not provided. */
-
-
-#include <libintl.h>
-#include <setjmp.h>
-#include <stdbool.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <stdio.h>
-
-/* This structure communicates state between _dl_catch_error and
- _dl_signal_error. */
-struct catch
- {
- const char **objname; /* Object/File name. */
- const char **errstring; /* Error detail filled in here. */
- bool *malloced; /* Nonzero if the string is malloced
- by the libc malloc. */
- volatile int *errcode; /* Return value of _dl_signal_error. */
- jmp_buf env; /* longjmp here on error. */
- };
-
-/* Multiple threads at once can use the `_dl_catch_error' function. The
- calls can come from `_dl_map_object_deps', `_dlerror_run', or from
- any of the libc functionality which loads dynamic objects (NSS, iconv).
- Therefore we have to be prepared to save the state in thread-local
- memory. */
-#if !DL_ERROR_BOOTSTRAP
-static __thread struct catch *catch_hook attribute_tls_model_ie;
-#else
-/* The version of this code in ld.so cannot use thread-local variables
- and is used during bootstrap only. */
-static struct catch *catch_hook;
-#endif
-
-/* This message we return as a last resort. We define the string in a
- variable since we have to avoid freeing it and so have to enable
- a pointer comparison. See below and in dlfcn/dlerror.c. */
-static const char _dl_out_of_memory[] = "out of memory";
-
-#if DL_ERROR_BOOTSTRAP
-/* This points to a function which is called when an continuable error is
- received. Unlike the handling of `catch' this function may return.
- The arguments will be the `errstring' and `objname'.
-
- Since this functionality is not used in normal programs (only in ld.so)
- we do not care about multi-threaded programs here. We keep this as a
- global variable. */
-static receiver_fct receiver;
-#endif /* DL_ERROR_BOOTSTRAP */
-
-void
-internal_function
-_dl_signal_error (int errcode, const char *objname, const char *occation,
- const char *errstring)
-{
- struct catch *lcatch = catch_hook;
-
- if (! errstring)
- errstring = N_("DYNAMIC LINKER BUG!!!");
-
- if (objname == NULL)
- objname = "";
- if (lcatch != NULL)
- {
- /* We are inside _dl_catch_error. Return to it. We have to
- duplicate the error string since it might be allocated on the
- stack. The object name is always a string constant. */
- size_t len_objname = strlen (objname) + 1;
- size_t len_errstring = strlen (errstring) + 1;
-
- char *errstring_copy = malloc (len_objname + len_errstring);
- if (errstring_copy != NULL)
- {
- /* Make a copy of the object file name and the error string. */
- *lcatch->objname = memcpy (__mempcpy (errstring_copy,
- errstring, len_errstring),
- objname, len_objname);
- *lcatch->errstring = errstring_copy;
-
- /* If the main executable is relocated it means the libc's malloc
- is used. */
- bool malloced = true;
-#ifdef SHARED
- malloced = (GL(dl_ns)[LM_ID_BASE]._ns_loaded != NULL
- && (GL(dl_ns)[LM_ID_BASE]._ns_loaded->l_relocated != 0));
-#endif
- *lcatch->malloced = malloced;
- }
- else
- {
- /* This is better than nothing. */
- *lcatch->objname = "";
- *lcatch->errstring = _dl_out_of_memory;
- *lcatch->malloced = false;
- }
-
- *lcatch->errcode = errcode;
-
- /* We do not restore the signal mask because none was saved. */
- __longjmp (lcatch->env[0].__jmpbuf, 1);
- }
- else
- {
- /* Lossage while resolving the program's own symbols is always fatal. */
- char buffer[1024];
- _dl_fatal_printf ("%s: %s: %s%s%s%s%s\n",
- RTLD_PROGNAME,
- occation ?: N_("error while loading shared libraries"),
- objname, *objname ? ": " : "",
- errstring, errcode ? ": " : "",
- (errcode
- ? __strerror_r (errcode, buffer, sizeof buffer)
- : ""));
- }
-}
-libc_hidden_def (_dl_signal_error)
-
-
-#if DL_ERROR_BOOTSTRAP
-void
-internal_function
-_dl_signal_cerror (int errcode, const char *objname, const char *occation,
- const char *errstring)
-{
- if (__builtin_expect (GLRO(dl_debug_mask)
- & ~(DL_DEBUG_STATISTICS|DL_DEBUG_PRELINK), 0))
- _dl_debug_printf ("%s: error: %s: %s (%s)\n", objname, occation,
- errstring, receiver ? "continued" : "fatal");
-
- if (receiver)
- {
- /* We are inside _dl_receive_error. Call the user supplied
- handler and resume the work. The receiver will still be
- installed. */
- (*receiver) (errcode, objname, errstring);
- }
- else
- _dl_signal_error (errcode, objname, occation, errstring);
-}
-#endif /* DL_ERROR_BOOTSTRAP */
-
-
-int
-internal_function
-_dl_catch_error (const char **objname, const char **errstring,
- bool *mallocedp, void (*operate) (void *), void *args)
-{
- /* We need not handle `receiver' since setting a `catch' is handled
- before it. */
-
- /* Only this needs to be marked volatile, because it is the only local
- variable that gets changed between the setjmp invocation and the
- longjmp call. All others are just set here (before setjmp) and read
- in _dl_signal_error (before longjmp). */
- volatile int errcode;
-
- struct catch c;
- /* Don't use an initializer since we don't need to clear C.env. */
- c.objname = objname;
- c.errstring = errstring;
- c.malloced = mallocedp;
- c.errcode = &errcode;
-
- struct catch *const old = catch_hook;
- catch_hook = &c;
-
- /* Do not save the signal mask. */
- if (__builtin_expect (__sigsetjmp (c.env, 0), 0) == 0)
- {
- (*operate) (args);
- catch_hook = old;
- *objname = NULL;
- *errstring = NULL;
- *mallocedp = false;
- return 0;
- }
-
- /* We get here only if we longjmp'd out of OPERATE. _dl_signal_error has
- already stored values into *OBJNAME, *ERRSTRING, and *MALLOCEDP. */
- catch_hook = old;
- return errcode;
-}
-libc_hidden_def (_dl_catch_error)
-
-#if DL_ERROR_BOOTSTRAP
-void
-internal_function
-_dl_receive_error (receiver_fct fct, void (*operate) (void *), void *args)
-{
- struct catch *old_catch = catch_hook;
- receiver_fct old_receiver = receiver;
-
- /* Set the new values. */
- catch_hook = NULL;
- receiver = fct;
-
- (*operate) (args);
-
- catch_hook = old_catch;
- receiver = old_receiver;
-}
-#endif /* DL_ERROR_BOOTSTRAP */
diff --git a/elf/dl-error.c b/elf/dl-error.c
deleted file mode 100644
index bfcbd5358b..0000000000
--- a/elf/dl-error.c
+++ /dev/null
@@ -1,27 +0,0 @@
-/* Error handling for runtime dynamic linker, full version.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This implementation lives in libc.so because it uses thread-local
- data, which is not available in ld.so. It interposes the version
- in dl-error-minimal.c after ld.so bootstrap.
-
- The signal/catch mechanism is used by the audit framework, which
- means that even in ld.so, not all errors are fatal. */
-
-#define DL_ERROR_BOOTSTRAP 0
-#include "dl-error-skeleton.c"
diff --git a/elf/dl-execstack.c b/elf/dl-execstack.c
deleted file mode 100644
index 875338bea5..0000000000
--- a/elf/dl-execstack.c
+++ /dev/null
@@ -1,31 +0,0 @@
-/* Stack executability handling for GNU dynamic linker. Stub version.
- Copyright (C) 2003-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <ldsodefs.h>
-#include <errno.h>
-
-/* There is no portable way to know the bounds of the initial thread's stack
- so as to mprotect it. */
-
-int
-internal_function
-_dl_make_stack_executable (void **stack_endp)
-{
- return ENOSYS;
-}
-rtld_hidden_def (_dl_make_stack_executable)
diff --git a/elf/dl-fini.c b/elf/dl-fini.c
deleted file mode 100644
index 93b337bea1..0000000000
--- a/elf/dl-fini.c
+++ /dev/null
@@ -1,281 +0,0 @@
-/* Call the termination functions of loaded shared objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <string.h>
-#include <ldsodefs.h>
-
-
-/* Type of the constructor functions. */
-typedef void (*fini_t) (void);
-
-
-void
-internal_function
-_dl_sort_fini (struct link_map **maps, size_t nmaps, char *used, Lmid_t ns)
-{
- /* A list of one element need not be sorted. */
- if (nmaps == 1)
- return;
-
- /* We can skip looking for the binary itself which is at the front
- of the search list for the main namespace. */
- unsigned int i = ns == LM_ID_BASE;
- uint16_t seen[nmaps];
- memset (seen, 0, nmaps * sizeof (seen[0]));
- while (1)
- {
- /* Keep track of which object we looked at this round. */
- ++seen[i];
- struct link_map *thisp = maps[i];
-
- /* Do not handle ld.so in secondary namespaces and object which
- are not removed. */
- if (thisp != thisp->l_real || thisp->l_idx == -1)
- goto skip;
-
- /* Find the last object in the list for which the current one is
- a dependency and move the current object behind the object
- with the dependency. */
- unsigned int k = nmaps - 1;
- while (k > i)
- {
- struct link_map **runp = maps[k]->l_initfini;
- if (runp != NULL)
- /* Look through the dependencies of the object. */
- while (*runp != NULL)
- if (__glibc_unlikely (*runp++ == thisp))
- {
- move:
- /* Move the current object to the back past the last
- object with it as the dependency. */
- memmove (&maps[i], &maps[i + 1],
- (k - i) * sizeof (maps[0]));
- maps[k] = thisp;
-
- if (used != NULL)
- {
- char here_used = used[i];
- memmove (&used[i], &used[i + 1],
- (k - i) * sizeof (used[0]));
- used[k] = here_used;
- }
-
- if (seen[i + 1] > nmaps - i)
- {
- ++i;
- goto next_clear;
- }
-
- uint16_t this_seen = seen[i];
- memmove (&seen[i], &seen[i + 1], (k - i) * sizeof (seen[0]));
- seen[k] = this_seen;
-
- goto next;
- }
-
- if (__glibc_unlikely (maps[k]->l_reldeps != NULL))
- {
- unsigned int m = maps[k]->l_reldeps->act;
- struct link_map **relmaps = &maps[k]->l_reldeps->list[0];
-
- /* Look through the relocation dependencies of the object. */
- while (m-- > 0)
- if (__glibc_unlikely (relmaps[m] == thisp))
- {
- /* If a cycle exists with a link time dependency,
- preserve the latter. */
- struct link_map **runp = thisp->l_initfini;
- if (runp != NULL)
- while (*runp != NULL)
- if (__glibc_unlikely (*runp++ == maps[k]))
- goto ignore;
- goto move;
- }
- ignore:;
- }
-
- --k;
- }
-
- skip:
- if (++i == nmaps)
- break;
- next_clear:
- memset (&seen[i], 0, (nmaps - i) * sizeof (seen[0]));
-
- next:;
- }
-}
-
-
-void
-internal_function
-_dl_fini (void)
-{
- /* Lots of fun ahead. We have to call the destructors for all still
- loaded objects, in all namespaces. The problem is that the ELF
- specification now demands that dependencies between the modules
- are taken into account. I.e., the destructor for a module is
- called before the ones for any of its dependencies.
-
- To make things more complicated, we cannot simply use the reverse
- order of the constructors. Since the user might have loaded objects
- using `dlopen' there are possibly several other modules with its
- dependencies to be taken into account. Therefore we have to start
- determining the order of the modules once again from the beginning. */
-
- /* We run the destructors of the main namespaces last. As for the
- other namespaces, we pick run the destructors in them in reverse
- order of the namespace ID. */
-#ifdef SHARED
- int do_audit = 0;
- again:
-#endif
- for (Lmid_t ns = GL(dl_nns) - 1; ns >= 0; --ns)
- {
- /* Protect against concurrent loads and unloads. */
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- unsigned int nloaded = GL(dl_ns)[ns]._ns_nloaded;
- /* No need to do anything for empty namespaces or those used for
- auditing DSOs. */
- if (nloaded == 0
-#ifdef SHARED
- || GL(dl_ns)[ns]._ns_loaded->l_auditing != do_audit
-#endif
- )
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- else
- {
- /* Now we can allocate an array to hold all the pointers and
- copy the pointers in. */
- struct link_map *maps[nloaded];
-
- unsigned int i;
- struct link_map *l;
- assert (nloaded != 0 || GL(dl_ns)[ns]._ns_loaded == NULL);
- for (l = GL(dl_ns)[ns]._ns_loaded, i = 0; l != NULL; l = l->l_next)
- /* Do not handle ld.so in secondary namespaces. */
- if (l == l->l_real)
- {
- assert (i < nloaded);
-
- maps[i] = l;
- l->l_idx = i;
- ++i;
-
- /* Bump l_direct_opencount of all objects so that they
- are not dlclose()ed from underneath us. */
- ++l->l_direct_opencount;
- }
- assert (ns != LM_ID_BASE || i == nloaded);
- assert (ns == LM_ID_BASE || i == nloaded || i == nloaded - 1);
- unsigned int nmaps = i;
-
- /* Now we have to do the sorting. */
- _dl_sort_fini (maps, nmaps, NULL, ns);
-
- /* We do not rely on the linked list of loaded object anymore
- from this point on. We have our own list here (maps). The
- various members of this list cannot vanish since the open
- count is too high and will be decremented in this loop. So
- we release the lock so that some code which might be called
- from a destructor can directly or indirectly access the
- lock. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- /* 'maps' now contains the objects in the right order. Now
- call the destructors. We have to process this array from
- the front. */
- for (i = 0; i < nmaps; ++i)
- {
- struct link_map *l = maps[i];
-
- if (l->l_init_called)
- {
- /* Make sure nothing happens if we are called twice. */
- l->l_init_called = 0;
-
- /* Is there a destructor function? */
- if (l->l_info[DT_FINI_ARRAY] != NULL
- || l->l_info[DT_FINI] != NULL)
- {
- /* When debugging print a message first. */
- if (__builtin_expect (GLRO(dl_debug_mask)
- & DL_DEBUG_IMPCALLS, 0))
- _dl_debug_printf ("\ncalling fini: %s [%lu]\n\n",
- DSO_FILENAME (l->l_name),
- ns);
-
- /* First see whether an array is given. */
- if (l->l_info[DT_FINI_ARRAY] != NULL)
- {
- ElfW(Addr) *array =
- (ElfW(Addr) *) (l->l_addr
- + l->l_info[DT_FINI_ARRAY]->d_un.d_ptr);
- unsigned int i = (l->l_info[DT_FINI_ARRAYSZ]->d_un.d_val
- / sizeof (ElfW(Addr)));
- while (i-- > 0)
- ((fini_t) array[i]) ();
- }
-
- /* Next try the old-style destructor. */
- if (l->l_info[DT_FINI] != NULL)
- DL_CALL_DT_FINI
- (l, l->l_addr + l->l_info[DT_FINI]->d_un.d_ptr);
- }
-
-#ifdef SHARED
- /* Auditing checkpoint: another object closed. */
- if (!do_audit && __builtin_expect (GLRO(dl_naudit) > 0, 0))
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objclose != NULL)
- /* Return value is ignored. */
- (void) afct->objclose (&l->l_audit[cnt].cookie);
-
- afct = afct->next;
- }
- }
-#endif
- }
-
- /* Correct the previous increment. */
- --l->l_direct_opencount;
- }
- }
- }
-
-#ifdef SHARED
- if (! do_audit && GLRO(dl_naudit) > 0)
- {
- do_audit = 1;
- goto again;
- }
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_STATISTICS))
- _dl_debug_printf ("\nruntime linker statistics:\n"
- " final number of relocations: %lu\n"
- "final number of relocations from cache: %lu\n",
- GL(dl_num_relocations),
- GL(dl_num_cache_relocations));
-#endif
-}
diff --git a/elf/dl-fptr.c b/elf/dl-fptr.c
deleted file mode 100644
index bf8ae43b51..0000000000
--- a/elf/dl-fptr.c
+++ /dev/null
@@ -1,322 +0,0 @@
-/* Manage function descriptors. Generic version.
- Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <libintl.h>
-#include <unistd.h>
-#include <string.h>
-#include <sys/param.h>
-#include <sys/mman.h>
-#include <link.h>
-#include <ldsodefs.h>
-#include <elf/dynamic-link.h>
-#include <dl-fptr.h>
-#include <dl-unmap-segments.h>
-#include <atomic.h>
-
-#ifndef ELF_MACHINE_BOOT_FPTR_TABLE_LEN
-/* ELF_MACHINE_BOOT_FPTR_TABLE_LEN should be greater than the number of
- dynamic symbols in ld.so. */
-# define ELF_MACHINE_BOOT_FPTR_TABLE_LEN 256
-#endif
-
-#ifndef ELF_MACHINE_LOAD_ADDRESS
-# error "ELF_MACHINE_LOAD_ADDRESS is not defined."
-#endif
-
-#ifndef COMPARE_AND_SWAP
-# define COMPARE_AND_SWAP(ptr, old, new) \
- (catomic_compare_and_exchange_bool_acq (ptr, new, old) == 0)
-#endif
-
-ElfW(Addr) _dl_boot_fptr_table [ELF_MACHINE_BOOT_FPTR_TABLE_LEN];
-
-static struct local
- {
- struct fdesc_table *root;
- struct fdesc *free_list;
- unsigned int npages; /* # of pages to allocate */
- /* the next to members MUST be consecutive! */
- struct fdesc_table boot_table;
- struct fdesc boot_fdescs[1024];
- }
-local =
- {
- .root = &local.boot_table,
- .npages = 2,
- .boot_table =
- {
- .len = sizeof (local.boot_fdescs) / sizeof (local.boot_fdescs[0]),
- .first_unused = 0
- }
- };
-
-/* Create a new fdesc table and return a pointer to the first fdesc
- entry. The fdesc lock must have been acquired already. */
-
-static struct fdesc_table *
-new_fdesc_table (struct local *l, size_t *size)
-{
- size_t old_npages = l->npages;
- size_t new_npages = old_npages + old_npages;
- struct fdesc_table *new_table;
-
- /* If someone has just created a new table, we return NULL to tell
- the caller to use the new table. */
- if (! COMPARE_AND_SWAP (&l->npages, old_npages, new_npages))
- return (struct fdesc_table *) NULL;
-
- *size = old_npages * GLRO(dl_pagesize);
- new_table = __mmap (NULL, *size,
- PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0);
- if (new_table == MAP_FAILED)
- _dl_signal_error (errno, NULL, NULL,
- N_("cannot map pages for fdesc table"));
-
- new_table->len
- = (*size - sizeof (*new_table)) / sizeof (struct fdesc);
- new_table->first_unused = 1;
- return new_table;
-}
-
-
-static ElfW(Addr)
-make_fdesc (ElfW(Addr) ip, ElfW(Addr) gp)
-{
- struct fdesc *fdesc = NULL;
- struct fdesc_table *root;
- unsigned int old;
- struct local *l;
-
- ELF_MACHINE_LOAD_ADDRESS (l, local);
-
- retry:
- root = l->root;
- while (1)
- {
- old = root->first_unused;
- if (old >= root->len)
- break;
- else if (COMPARE_AND_SWAP (&root->first_unused, old, old + 1))
- {
- fdesc = &root->fdesc[old];
- goto install;
- }
- }
-
- if (l->free_list)
- {
- /* Get it from free-list. */
- do
- {
- fdesc = l->free_list;
- if (fdesc == NULL)
- goto retry;
- }
- while (! COMPARE_AND_SWAP ((ElfW(Addr) *) &l->free_list,
- (ElfW(Addr)) fdesc, fdesc->ip));
- }
- else
- {
- /* Create a new fdesc table. */
- size_t size;
- struct fdesc_table *new_table = new_fdesc_table (l, &size);
-
- if (new_table == NULL)
- goto retry;
-
- new_table->next = root;
- if (! COMPARE_AND_SWAP ((ElfW(Addr) *) &l->root,
- (ElfW(Addr)) root,
- (ElfW(Addr)) new_table))
- {
- /* Someone has just installed a new table. Return NULL to
- tell the caller to use the new table. */
- __munmap (new_table, size);
- goto retry;
- }
-
- /* Note that the first entry was reserved while allocating the
- memory for the new page. */
- fdesc = &new_table->fdesc[0];
- }
-
- install:
- fdesc->ip = ip;
- fdesc->gp = gp;
-
- return (ElfW(Addr)) fdesc;
-}
-
-
-static inline ElfW(Addr) * __attribute__ ((always_inline))
-make_fptr_table (struct link_map *map)
-{
- const ElfW(Sym) *symtab
- = (const void *) D_PTR (map, l_info[DT_SYMTAB]);
- const char *strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
- ElfW(Addr) *fptr_table;
- size_t size;
- size_t len;
-
- /* XXX Apparently the only way to find out the size of the dynamic
- symbol section is to assume that the string table follows right
- afterwards... */
- len = ((strtab - (char *) symtab)
- / map->l_info[DT_SYMENT]->d_un.d_val);
- size = ((len * sizeof (fptr_table[0]) + GLRO(dl_pagesize) - 1)
- & -GLRO(dl_pagesize));
- /* XXX We don't support here in the moment systems without MAP_ANON.
- There probably are none for IA-64. In case this is proven wrong
- we will have to open /dev/null here and use the file descriptor
- instead of the hard-coded -1. */
- fptr_table = __mmap (NULL, size,
- PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE,
- -1, 0);
- if (fptr_table == MAP_FAILED)
- _dl_signal_error (errno, NULL, NULL,
- N_("cannot map pages for fptr table"));
-
- if (COMPARE_AND_SWAP ((ElfW(Addr) *) &map->l_mach.fptr_table,
- (ElfW(Addr)) NULL, (ElfW(Addr)) fptr_table))
- map->l_mach.fptr_table_len = len;
- else
- __munmap (fptr_table, len * sizeof (fptr_table[0]));
-
- return map->l_mach.fptr_table;
-}
-
-
-ElfW(Addr)
-_dl_make_fptr (struct link_map *map, const ElfW(Sym) *sym,
- ElfW(Addr) ip)
-{
- ElfW(Addr) *ftab = map->l_mach.fptr_table;
- const ElfW(Sym) *symtab;
- Elf_Symndx symidx;
- struct local *l;
-
- if (__glibc_unlikely (ftab == NULL))
- ftab = make_fptr_table (map);
-
- symtab = (const void *) D_PTR (map, l_info[DT_SYMTAB]);
- symidx = sym - symtab;
-
- if (symidx >= map->l_mach.fptr_table_len)
- _dl_signal_error (0, NULL, NULL,
- N_("internal error: symidx out of range of fptr table"));
-
- while (ftab[symidx] == 0)
- {
- /* GOT has already been relocated in elf_get_dynamic_info -
- don't try to relocate it again. */
- ElfW(Addr) fdesc
- = make_fdesc (ip, map->l_info[DT_PLTGOT]->d_un.d_ptr);
-
- if (__builtin_expect (COMPARE_AND_SWAP (&ftab[symidx], (ElfW(Addr)) NULL,
- fdesc), 1))
- {
- /* Noone has updated the entry and the new function
- descriptor has been installed. */
-#if 0
- const char *strtab
- = (const void *) D_PTR (map, l_info[DT_STRTAB]);
-
- ELF_MACHINE_LOAD_ADDRESS (l, local);
- if (l->root != &l->boot_table
- || l->boot_table.first_unused > 20)
- _dl_debug_printf ("created fdesc symbol `%s' at %lx\n",
- strtab + sym->st_name, ftab[symidx]);
-#endif
- break;
- }
- else
- {
- /* We created a duplicated function descriptor. We put it on
- free-list. */
- struct fdesc *f = (struct fdesc *) fdesc;
-
- ELF_MACHINE_LOAD_ADDRESS (l, local);
-
- do
- f->ip = (ElfW(Addr)) l->free_list;
- while (! COMPARE_AND_SWAP ((ElfW(Addr) *) &l->free_list,
- f->ip, fdesc));
- }
- }
-
- return ftab[symidx];
-}
-
-
-void
-_dl_unmap (struct link_map *map)
-{
- ElfW(Addr) *ftab = map->l_mach.fptr_table;
- struct fdesc *head = NULL, *tail = NULL;
- size_t i;
-
- _dl_unmap_segments (map);
-
- if (ftab == NULL)
- return;
-
- /* String together the fdesc structures that are being freed. */
- for (i = 0; i < map->l_mach.fptr_table_len; ++i)
- {
- if (ftab[i])
- {
- *(struct fdesc **) ftab[i] = head;
- head = (struct fdesc *) ftab[i];
- if (tail == NULL)
- tail = head;
- }
- }
-
- /* Prepend the new list to the free_list: */
- if (tail)
- do
- tail->ip = (ElfW(Addr)) local.free_list;
- while (! COMPARE_AND_SWAP ((ElfW(Addr) *) &local.free_list,
- tail->ip, (ElfW(Addr)) head));
-
- __munmap (ftab, (map->l_mach.fptr_table_len
- * sizeof (map->l_mach.fptr_table[0])));
-
- map->l_mach.fptr_table = NULL;
-}
-
-
-ElfW(Addr)
-_dl_lookup_address (const void *address)
-{
- ElfW(Addr) addr = (ElfW(Addr)) address;
- struct fdesc_table *t;
- unsigned long int i;
-
- for (t = local.root; t != NULL; t = t->next)
- {
- i = (struct fdesc *) addr - &t->fdesc[0];
- if (i < t->first_unused && addr == (ElfW(Addr)) &t->fdesc[i])
- {
- addr = t->fdesc[i].ip;
- break;
- }
- }
-
- return addr;
-}
diff --git a/elf/dl-hwcaps.c b/elf/dl-hwcaps.c
deleted file mode 100644
index ac50fd2c38..0000000000
--- a/elf/dl-hwcaps.c
+++ /dev/null
@@ -1,297 +0,0 @@
-/* Hardware capability support for run-time dynamic loader.
- Copyright (C) 2012-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <elf.h>
-#include <errno.h>
-#include <libintl.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-
-#include <dl-procinfo.h>
-#include <dl-hwcaps.h>
-
-#ifdef _DL_FIRST_PLATFORM
-# define _DL_FIRST_EXTRA (_DL_FIRST_PLATFORM + _DL_PLATFORMS_COUNT)
-#else
-# define _DL_FIRST_EXTRA _DL_HWCAP_COUNT
-#endif
-
-/* Return an array of useful/necessary hardware capability names. */
-const struct r_strlenpair *
-internal_function
-_dl_important_hwcaps (const char *platform, size_t platform_len, size_t *sz,
- size_t *max_capstrlen)
-{
- uint64_t hwcap_mask = GET_HWCAP_MASK();
- /* Determine how many important bits are set. */
- uint64_t masked = GLRO(dl_hwcap) & hwcap_mask;
- size_t cnt = platform != NULL;
- size_t n, m;
- size_t total;
- struct r_strlenpair *result;
- struct r_strlenpair *rp;
- char *cp;
-
- /* Count the number of bits set in the masked value. */
- for (n = 0; (~((1ULL << n) - 1) & masked) != 0; ++n)
- if ((masked & (1ULL << n)) != 0)
- ++cnt;
-
-#ifdef NEED_DL_SYSINFO_DSO
- /* The system-supplied DSO can contain a note of type 2, vendor "GNU".
- This gives us a list of names to treat as fake hwcap bits. */
-
- const char *dsocaps = NULL;
- size_t dsocapslen = 0;
- if (GLRO(dl_sysinfo_map) != NULL)
- {
- const ElfW(Phdr) *const phdr = GLRO(dl_sysinfo_map)->l_phdr;
- const ElfW(Word) phnum = GLRO(dl_sysinfo_map)->l_phnum;
- for (uint_fast16_t i = 0; i < phnum; ++i)
- if (phdr[i].p_type == PT_NOTE)
- {
- const ElfW(Addr) start = (phdr[i].p_vaddr
- + GLRO(dl_sysinfo_map)->l_addr);
- /* The standard ELF note layout is exactly as the anonymous struct.
- The next element is a variable length vendor name of length
- VENDORLEN (with a real length rounded to ElfW(Word)), followed
- by the data of length DATALEN (with a real length rounded to
- ElfW(Word)). */
- const struct
- {
- ElfW(Word) vendorlen;
- ElfW(Word) datalen;
- ElfW(Word) type;
- } *note = (const void *) start;
- while ((ElfW(Addr)) (note + 1) - start < phdr[i].p_memsz)
- {
-#define ROUND(len) (((len) + sizeof (ElfW(Word)) - 1) & -sizeof (ElfW(Word)))
- /* The layout of the type 2, vendor "GNU" note is as follows:
- .long <Number of capabilities enabled by this note>
- .long <Capabilities mask> (as mask >> _DL_FIRST_EXTRA).
- .byte <The bit number for the next capability>
- .asciz <The name of the capability>. */
- if (note->type == NT_GNU_HWCAP
- && note->vendorlen == sizeof "GNU"
- && !memcmp ((note + 1), "GNU", sizeof "GNU")
- && note->datalen > 2 * sizeof (ElfW(Word)) + 2)
- {
- const ElfW(Word) *p = ((const void *) (note + 1)
- + ROUND (sizeof "GNU"));
- cnt += *p++;
- ++p; /* Skip mask word. */
- dsocaps = (const char *) p; /* Pseudo-string "<b>name" */
- dsocapslen = note->datalen - sizeof *p * 2;
- break;
- }
- note = ((const void *) (note + 1)
- + ROUND (note->vendorlen) + ROUND (note->datalen));
-#undef ROUND
- }
- if (dsocaps != NULL)
- break;
- }
- }
-#endif
-
- /* For TLS enabled builds always add 'tls'. */
- ++cnt;
-
- /* Create temporary data structure to generate result table. */
- struct r_strlenpair temp[cnt];
- m = 0;
-#ifdef NEED_DL_SYSINFO_DSO
- if (dsocaps != NULL)
- {
- /* dsocaps points to the .asciz string, and -1 points to the mask
- .long just before the string. */
- const ElfW(Word) mask = ((const ElfW(Word) *) dsocaps)[-1];
- GLRO(dl_hwcap) |= (uint64_t) mask << _DL_FIRST_EXTRA;
- /* Note that we add the dsocaps to the set already chosen by the
- LD_HWCAP_MASK environment variable (or default HWCAP_IMPORTANT).
- So there is no way to request ignoring an OS-supplied dsocap
- string and bit like you can ignore an OS-supplied HWCAP bit. */
- hwcap_mask |= (uint64_t) mask << _DL_FIRST_EXTRA;
-#if HAVE_TUNABLES
- TUNABLE_SET (glibc, tune, hwcap_mask, uint64_t, hwcap_mask);
-#else
- GLRO(dl_hwcap_mask) = hwcap_mask;
-#endif
- size_t len;
- for (const char *p = dsocaps; p < dsocaps + dsocapslen; p += len + 1)
- {
- uint_fast8_t bit = *p++;
- len = strlen (p);
-
- /* Skip entries that are not enabled in the mask word. */
- if (__glibc_likely (mask & ((ElfW(Word)) 1 << bit)))
- {
- temp[m].str = p;
- temp[m].len = len;
- ++m;
- }
- else
- --cnt;
- }
- }
-#endif
- for (n = 0; masked != 0; ++n)
- if ((masked & (1ULL << n)) != 0)
- {
- temp[m].str = _dl_hwcap_string (n);
- temp[m].len = strlen (temp[m].str);
- masked ^= 1ULL << n;
- ++m;
- }
- if (platform != NULL)
- {
- temp[m].str = platform;
- temp[m].len = platform_len;
- ++m;
- }
-
- temp[m].str = "tls";
- temp[m].len = 3;
- ++m;
-
- assert (m == cnt);
-
- /* Determine the total size of all strings together. */
- if (cnt == 1)
- total = temp[0].len + 1;
- else
- {
- total = temp[0].len + temp[cnt - 1].len + 2;
- if (cnt > 2)
- {
- total <<= 1;
- for (n = 1; n + 1 < cnt; ++n)
- total += temp[n].len + 1;
- if (cnt > 3
- && (cnt >= sizeof (size_t) * 8
- || total + (sizeof (*result) << 3)
- >= (1UL << (sizeof (size_t) * 8 - cnt + 3))))
- _dl_signal_error (ENOMEM, NULL, NULL,
- N_("cannot create capability list"));
-
- total <<= cnt - 3;
- }
- }
-
- /* The result structure: we use a very compressed way to store the
- various combinations of capability names. */
- *sz = 1 << cnt;
- result = (struct r_strlenpair *) malloc (*sz * sizeof (*result) + total);
- if (result == NULL)
- _dl_signal_error (ENOMEM, NULL, NULL,
- N_("cannot create capability list"));
-
- if (cnt == 1)
- {
- result[0].str = (char *) (result + *sz);
- result[0].len = temp[0].len + 1;
- result[1].str = (char *) (result + *sz);
- result[1].len = 0;
- cp = __mempcpy ((char *) (result + *sz), temp[0].str, temp[0].len);
- *cp = '/';
- *sz = 2;
- *max_capstrlen = result[0].len;
-
- return result;
- }
-
- /* Fill in the information. This follows the following scheme
- (indices from TEMP for four strings):
- entry #0: 0, 1, 2, 3 binary: 1111
- #1: 0, 1, 3 1101
- #2: 0, 2, 3 1011
- #3: 0, 3 1001
- This allows the representation of all possible combinations of
- capability names in the string. First generate the strings. */
- result[1].str = result[0].str = cp = (char *) (result + *sz);
-#define add(idx) \
- cp = __mempcpy (__mempcpy (cp, temp[idx].str, temp[idx].len), "/", 1);
- if (cnt == 2)
- {
- add (1);
- add (0);
- }
- else
- {
- n = 1 << (cnt - 1);
- do
- {
- n -= 2;
-
- /* We always add the last string. */
- add (cnt - 1);
-
- /* Add the strings which have the bit set in N. */
- for (m = cnt - 2; m > 0; --m)
- if ((n & (1 << m)) != 0)
- add (m);
-
- /* Always add the first string. */
- add (0);
- }
- while (n != 0);
- }
-#undef add
-
- /* Now we are ready to install the string pointers and length. */
- for (n = 0; n < (1UL << cnt); ++n)
- result[n].len = 0;
- n = cnt;
- do
- {
- size_t mask = 1 << --n;
-
- rp = result;
- for (m = 1 << cnt; m > 0; ++rp)
- if ((--m & mask) != 0)
- rp->len += temp[n].len + 1;
- }
- while (n != 0);
-
- /* The first half of the strings all include the first string. */
- n = (1 << cnt) - 2;
- rp = &result[2];
- while (n != (1UL << (cnt - 1)))
- {
- if ((--n & 1) != 0)
- rp[0].str = rp[-2].str + rp[-2].len;
- else
- rp[0].str = rp[-1].str;
- ++rp;
- }
-
- /* The second half starts right after the first part of the string of
- the corresponding entry in the first half. */
- do
- {
- rp[0].str = rp[-(1 << (cnt - 1))].str + temp[cnt - 1].len + 1;
- ++rp;
- }
- while (--n != 0);
-
- /* The maximum string length. */
- *max_capstrlen = result[0].len;
-
- return result;
-}
diff --git a/elf/dl-hwcaps.h b/elf/dl-hwcaps.h
deleted file mode 100644
index 2c4fa3db02..0000000000
--- a/elf/dl-hwcaps.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Hardware capability support for run-time dynamic loader.
- Copyright (C) 2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <elf/dl-tunables.h>
-
-#if HAVE_TUNABLES
-# define GET_HWCAP_MASK() TUNABLE_GET (glibc, tune, hwcap_mask, uint64_t, NULL)
-#else
-# ifdef SHARED
-# define GET_HWCAP_MASK() GLRO(dl_hwcap_mask)
-# else
-/* HWCAP_MASK is ignored in static binaries when built without tunables. */
-# define GET_HWCAP_MASK() (0)
-# endif
-#endif
diff --git a/elf/dl-init.c b/elf/dl-init.c
deleted file mode 100644
index 5c5f3de365..0000000000
--- a/elf/dl-init.c
+++ /dev/null
@@ -1,126 +0,0 @@
-/* Run initializers for newly loaded objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stddef.h>
-#include <ldsodefs.h>
-
-
-/* Type of the initializer. */
-typedef void (*init_t) (int, char **, char **);
-
-
-static void
-call_init (struct link_map *l, int argc, char **argv, char **env)
-{
- if (l->l_init_called)
- /* This object is all done. */
- return;
-
- /* Avoid handling this constructor again in case we have a circular
- dependency. */
- l->l_init_called = 1;
-
- /* Check for object which constructors we do not run here. */
- if (__builtin_expect (l->l_name[0], 'a') == '\0'
- && l->l_type == lt_executable)
- return;
-
- /* Are there any constructors? */
- if (l->l_info[DT_INIT] == NULL
- && __builtin_expect (l->l_info[DT_INIT_ARRAY] == NULL, 1))
- return;
-
- /* Print a debug message if wanted. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_IMPCALLS))
- _dl_debug_printf ("\ncalling init: %s\n\n",
- DSO_FILENAME (l->l_name));
-
- /* Now run the local constructors. There are two forms of them:
- - the one named by DT_INIT
- - the others in the DT_INIT_ARRAY.
- */
- if (l->l_info[DT_INIT] != NULL)
- DL_CALL_DT_INIT(l, l->l_addr + l->l_info[DT_INIT]->d_un.d_ptr, argc, argv, env);
-
- /* Next see whether there is an array with initialization functions. */
- ElfW(Dyn) *init_array = l->l_info[DT_INIT_ARRAY];
- if (init_array != NULL)
- {
- unsigned int j;
- unsigned int jm;
- ElfW(Addr) *addrs;
-
- jm = l->l_info[DT_INIT_ARRAYSZ]->d_un.d_val / sizeof (ElfW(Addr));
-
- addrs = (ElfW(Addr) *) (init_array->d_un.d_ptr + l->l_addr);
- for (j = 0; j < jm; ++j)
- ((init_t) addrs[j]) (argc, argv, env);
- }
-}
-
-
-void
-internal_function
-_dl_init (struct link_map *main_map, int argc, char **argv, char **env)
-{
- ElfW(Dyn) *preinit_array = main_map->l_info[DT_PREINIT_ARRAY];
- ElfW(Dyn) *preinit_array_size = main_map->l_info[DT_PREINIT_ARRAYSZ];
- unsigned int i;
-
- if (__glibc_unlikely (GL(dl_initfirst) != NULL))
- {
- call_init (GL(dl_initfirst), argc, argv, env);
- GL(dl_initfirst) = NULL;
- }
-
- /* Don't do anything if there is no preinit array. */
- if (__builtin_expect (preinit_array != NULL, 0)
- && preinit_array_size != NULL
- && (i = preinit_array_size->d_un.d_val / sizeof (ElfW(Addr))) > 0)
- {
- ElfW(Addr) *addrs;
- unsigned int cnt;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_IMPCALLS))
- _dl_debug_printf ("\ncalling preinit: %s\n\n",
- DSO_FILENAME (main_map->l_name));
-
- addrs = (ElfW(Addr) *) (preinit_array->d_un.d_ptr + main_map->l_addr);
- for (cnt = 0; cnt < i; ++cnt)
- ((init_t) addrs[cnt]) (argc, argv, env);
- }
-
- /* Stupid users forced the ELF specification to be changed. It now
- says that the dynamic loader is responsible for determining the
- order in which the constructors have to run. The constructors
- for all dependencies of an object must run before the constructor
- for the object itself. Circular dependencies are left unspecified.
-
- This is highly questionable since it puts the burden on the dynamic
- loader which has to find the dependencies at runtime instead of
- letting the user do it right. Stupidity rules! */
-
- i = main_map->l_searchlist.r_nlist;
- while (i-- > 0)
- call_init (main_map->l_initfini[i], argc, argv, env);
-
-#ifndef HAVE_INLINED_SYSCALLS
- /* Finished starting up. */
- _dl_starting_up = 0;
-#endif
-}
diff --git a/elf/dl-iteratephdr.c b/elf/dl-iteratephdr.c
deleted file mode 100644
index ddd5bde831..0000000000
--- a/elf/dl-iteratephdr.c
+++ /dev/null
@@ -1,89 +0,0 @@
-/* Get loaded objects program headers.
- Copyright (C) 2001-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2001.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public License as
- published by the Free Software Foundation; either version 2.1 of the
- License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; see the file COPYING.LIB. If
- not, see <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <ldsodefs.h>
-#include <stddef.h>
-#include <libc-lock.h>
-
-static void
-cancel_handler (void *arg __attribute__((unused)))
-{
- __rtld_lock_unlock_recursive (GL(dl_load_write_lock));
-}
-
-hidden_proto (__dl_iterate_phdr)
-int
-__dl_iterate_phdr (int (*callback) (struct dl_phdr_info *info,
- size_t size, void *data), void *data)
-{
- struct link_map *l;
- struct dl_phdr_info info;
- int ret = 0;
-
- /* Make sure nobody modifies the list of loaded objects. */
- __rtld_lock_lock_recursive (GL(dl_load_write_lock));
- __libc_cleanup_push (cancel_handler, NULL);
-
- /* We have to determine the namespace of the caller since this determines
- which namespace is reported. */
- size_t nloaded = GL(dl_ns)[0]._ns_nloaded;
- Lmid_t ns = 0;
-#ifdef SHARED
- const void *caller = RETURN_ADDRESS (0);
- for (Lmid_t cnt = GL(dl_nns) - 1; cnt > 0; --cnt)
- for (struct link_map *l = GL(dl_ns)[cnt]._ns_loaded; l; l = l->l_next)
- {
- /* We have to count the total number of loaded objects. */
- nloaded += GL(dl_ns)[cnt]._ns_nloaded;
-
- if (caller >= (const void *) l->l_map_start
- && caller < (const void *) l->l_map_end
- && (l->l_contiguous
- || _dl_addr_inside_object (l, (ElfW(Addr)) caller)))
- ns = cnt;
- }
-#endif
-
- for (l = GL(dl_ns)[ns]._ns_loaded; l != NULL; l = l->l_next)
- {
- info.dlpi_addr = l->l_real->l_addr;
- info.dlpi_name = l->l_real->l_name;
- info.dlpi_phdr = l->l_real->l_phdr;
- info.dlpi_phnum = l->l_real->l_phnum;
- info.dlpi_adds = GL(dl_load_adds);
- info.dlpi_subs = GL(dl_load_adds) - nloaded;
- info.dlpi_tls_data = NULL;
- info.dlpi_tls_modid = l->l_real->l_tls_modid;
- if (info.dlpi_tls_modid != 0)
- info.dlpi_tls_data = GLRO(dl_tls_get_addr_soft) (l->l_real);
- ret = callback (&info, sizeof (struct dl_phdr_info), data);
- if (ret)
- break;
- }
-
- /* Release the lock. */
- __libc_cleanup_pop (0);
- __rtld_lock_unlock_recursive (GL(dl_load_write_lock));
-
- return ret;
-}
-hidden_def (__dl_iterate_phdr)
-
-weak_alias (__dl_iterate_phdr, dl_iterate_phdr);
diff --git a/elf/dl-libc.c b/elf/dl-libc.c
deleted file mode 100644
index 9fdc8b1130..0000000000
--- a/elf/dl-libc.c
+++ /dev/null
@@ -1,330 +0,0 @@
-/* Handle loading and unloading shared objects for internal libc purposes.
- Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Zack Weinberg <zack@rabi.columbia.edu>, 1999.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <ldsodefs.h>
-
-extern int __libc_argc attribute_hidden;
-extern char **__libc_argv attribute_hidden;
-
-extern char **__environ;
-
-/* The purpose of this file is to provide wrappers around the dynamic
- linker error mechanism (similar to dlopen() et al in libdl) which
- are usable from within libc. Generally we want to throw away the
- string that dlerror() would return and just pass back a null pointer
- for errors. This also lets the rest of libc not know about the error
- handling mechanism.
-
- Much of this code came from gconv_dl.c with slight modifications. */
-
-static int
-internal_function
-dlerror_run (void (*operate) (void *), void *args)
-{
- const char *objname;
- const char *last_errstring = NULL;
- bool malloced;
-
- int result = (_dl_catch_error (&objname, &last_errstring, &malloced,
- operate, args)
- ?: last_errstring != NULL);
-
- if (result && malloced)
- free ((char *) last_errstring);
-
- return result;
-}
-
-/* These functions are called by dlerror_run... */
-
-struct do_dlopen_args
-{
- /* Argument to do_dlopen. */
- const char *name;
- /* Opening mode. */
- int mode;
- /* This is the caller of the dlopen() function. */
- const void *caller_dlopen;
-
- /* Return from do_dlopen. */
- struct link_map *map;
-};
-
-struct do_dlsym_args
-{
- /* Arguments to do_dlsym. */
- struct link_map *map;
- const char *name;
-
- /* Return values of do_dlsym. */
- lookup_t loadbase;
- const ElfW(Sym) *ref;
-};
-
-static void
-do_dlopen (void *ptr)
-{
- struct do_dlopen_args *args = (struct do_dlopen_args *) ptr;
- /* Open and relocate the shared object. */
- args->map = GLRO(dl_open) (args->name, args->mode, args->caller_dlopen,
- __LM_ID_CALLER, __libc_argc, __libc_argv,
- __environ);
-}
-
-static void
-do_dlsym (void *ptr)
-{
- struct do_dlsym_args *args = (struct do_dlsym_args *) ptr;
- args->ref = NULL;
- args->loadbase = GLRO(dl_lookup_symbol_x) (args->name, args->map, &args->ref,
- args->map->l_local_scope, NULL, 0,
- DL_LOOKUP_RETURN_NEWEST, NULL);
-}
-
-static void
-do_dlclose (void *ptr)
-{
- GLRO(dl_close) ((struct link_map *) ptr);
-}
-
-/* This code is to support __libc_dlopen from __libc_dlopen'ed shared
- libraries. We need to ensure the statically linked __libc_dlopen
- etc. functions are used instead of the dynamically loaded. */
-struct dl_open_hook
-{
- void *(*dlopen_mode) (const char *name, int mode);
- void *(*dlsym) (void *map, const char *name);
- int (*dlclose) (void *map);
-};
-
-#ifdef SHARED
-extern struct dl_open_hook *_dl_open_hook;
-libc_hidden_proto (_dl_open_hook);
-struct dl_open_hook *_dl_open_hook __attribute__ ((nocommon));
-libc_hidden_data_def (_dl_open_hook);
-#else
-static void
-do_dlsym_private (void *ptr)
-{
- lookup_t l;
- struct r_found_version vers;
- vers.name = "GLIBC_PRIVATE";
- vers.hidden = 1;
- /* vers.hash = _dl_elf_hash (vers.name); */
- vers.hash = 0x0963cf85;
- vers.filename = NULL;
-
- struct do_dlsym_args *args = (struct do_dlsym_args *) ptr;
- args->ref = NULL;
- l = GLRO(dl_lookup_symbol_x) (args->name, args->map, &args->ref,
- args->map->l_scope, &vers, 0, 0, NULL);
- args->loadbase = l;
-}
-
-static struct dl_open_hook _dl_open_hook =
- {
- .dlopen_mode = __libc_dlopen_mode,
- .dlsym = __libc_dlsym,
- .dlclose = __libc_dlclose
- };
-#endif
-
-/* ... and these functions call dlerror_run. */
-
-void *
-__libc_dlopen_mode (const char *name, int mode)
-{
- struct do_dlopen_args args;
- args.name = name;
- args.mode = mode;
- args.caller_dlopen = RETURN_ADDRESS (0);
-
-#ifdef SHARED
- if (__glibc_unlikely (_dl_open_hook != NULL))
- return _dl_open_hook->dlopen_mode (name, mode);
- return (dlerror_run (do_dlopen, &args) ? NULL : (void *) args.map);
-#else
- if (dlerror_run (do_dlopen, &args))
- return NULL;
-
- __libc_register_dl_open_hook (args.map);
- __libc_register_dlfcn_hook (args.map);
- return (void *) args.map;
-#endif
-}
-libc_hidden_def (__libc_dlopen_mode)
-
-#ifndef SHARED
-void *
-__libc_dlsym_private (struct link_map *map, const char *name)
-{
- struct do_dlsym_args sargs;
- sargs.map = map;
- sargs.name = name;
-
- if (! dlerror_run (do_dlsym_private, &sargs))
- return DL_SYMBOL_ADDRESS (sargs.loadbase, sargs.ref);
- return NULL;
-}
-
-void
-__libc_register_dl_open_hook (struct link_map *map)
-{
- struct dl_open_hook **hook;
-
- hook = (struct dl_open_hook **) __libc_dlsym_private (map, "_dl_open_hook");
- if (hook != NULL)
- *hook = &_dl_open_hook;
-}
-#endif
-
-void *
-__libc_dlsym (void *map, const char *name)
-{
- struct do_dlsym_args args;
- args.map = map;
- args.name = name;
-
-#ifdef SHARED
- if (__glibc_unlikely (_dl_open_hook != NULL))
- return _dl_open_hook->dlsym (map, name);
-#endif
- return (dlerror_run (do_dlsym, &args) ? NULL
- : (void *) (DL_SYMBOL_ADDRESS (args.loadbase, args.ref)));
-}
-libc_hidden_def (__libc_dlsym)
-
-int
-__libc_dlclose (void *map)
-{
-#ifdef SHARED
- if (__glibc_unlikely (_dl_open_hook != NULL))
- return _dl_open_hook->dlclose (map);
-#endif
- return dlerror_run (do_dlclose, map);
-}
-libc_hidden_def (__libc_dlclose)
-
-
-static bool __libc_freeres_fn_section
-free_slotinfo (struct dtv_slotinfo_list **elemp)
-{
- size_t cnt;
-
- if (*elemp == NULL)
- /* Nothing here, all is removed (or there never was anything). */
- return true;
-
- if (!free_slotinfo (&(*elemp)->next))
- /* We cannot free the entry. */
- return false;
-
- /* That cleared our next pointer for us. */
-
- for (cnt = 0; cnt < (*elemp)->len; ++cnt)
- if ((*elemp)->slotinfo[cnt].map != NULL)
- /* Still used. */
- return false;
-
- /* We can remove the list element. */
- free (*elemp);
- *elemp = NULL;
-
- return true;
-}
-
-
-libc_freeres_fn (free_mem)
-{
- struct link_map *l;
- struct r_search_path_elem *d;
-
- /* Remove all search directories. */
- d = GL(dl_all_dirs);
- while (d != GLRO(dl_init_all_dirs))
- {
- struct r_search_path_elem *old = d;
- d = d->next;
- free (old);
- }
-
- for (Lmid_t ns = 0; ns < GL(dl_nns); ++ns)
- {
- for (l = GL(dl_ns)[ns]._ns_loaded; l != NULL; l = l->l_next)
- {
- struct libname_list *lnp = l->l_libname->next;
-
- l->l_libname->next = NULL;
-
- /* Remove all additional names added to the objects. */
- while (lnp != NULL)
- {
- struct libname_list *old = lnp;
- lnp = lnp->next;
- if (! old->dont_free)
- free (old);
- }
-
- /* Free the initfini dependency list. */
- if (l->l_free_initfini)
- free (l->l_initfini);
- l->l_initfini = NULL;
- }
-
- if (__builtin_expect (GL(dl_ns)[ns]._ns_global_scope_alloc, 0) != 0
- && (GL(dl_ns)[ns]._ns_main_searchlist->r_nlist
- // XXX Check whether we need NS-specific initial_searchlist
- == GLRO(dl_initial_searchlist).r_nlist))
- {
- /* All object dynamically loaded by the program are unloaded. Free
- the memory allocated for the global scope variable. */
- struct link_map **old = GL(dl_ns)[ns]._ns_main_searchlist->r_list;
-
- /* Put the old map in. */
- GL(dl_ns)[ns]._ns_main_searchlist->r_list
- // XXX Check whether we need NS-specific initial_searchlist
- = GLRO(dl_initial_searchlist).r_list;
- /* Signal that the original map is used. */
- GL(dl_ns)[ns]._ns_global_scope_alloc = 0;
-
- /* Now free the old map. */
- free (old);
- }
- }
-
- /* Free the memory allocated for the dtv slotinfo array. We can do
- this only if all modules which used this memory are unloaded. */
-#ifdef SHARED
- if (GL(dl_initial_dtv) == NULL)
- /* There was no initial TLS setup, it was set up later when
- it used the normal malloc. */
- free_slotinfo (&GL(dl_tls_dtv_slotinfo_list));
- else
-#endif
- /* The first element of the list does not have to be deallocated.
- It was allocated in the dynamic linker (i.e., with a different
- malloc), and in the static library it's in .bss space. */
- free_slotinfo (&GL(dl_tls_dtv_slotinfo_list)->next);
-
- void *scope_free_list = GL(dl_scope_free_list);
- GL(dl_scope_free_list) = NULL;
- free (scope_free_list);
-}
diff --git a/elf/dl-load.c b/elf/dl-load.c
deleted file mode 100644
index c1b6d4ba0f..0000000000
--- a/elf/dl-load.c
+++ /dev/null
@@ -1,2307 +0,0 @@
-/* Map in a shared object's segments from the file.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <elf.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <libintl.h>
-#include <stdbool.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <bits/wordsize.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-#include <sys/types.h>
-#include "dynamic-link.h"
-#include <abi-tag.h>
-#include <stackinfo.h>
-#include <caller.h>
-#include <sysdep.h>
-#include <stap-probe.h>
-#include <libc-pointer-arith.h>
-
-#include <dl-dst.h>
-#include <dl-load.h>
-#include <dl-map-segments.h>
-#include <dl-unmap-segments.h>
-#include <dl-machine-reject-phdr.h>
-#include <dl-sysdep-open.h>
-
-
-#include <endian.h>
-#if BYTE_ORDER == BIG_ENDIAN
-# define byteorder ELFDATA2MSB
-#elif BYTE_ORDER == LITTLE_ENDIAN
-# define byteorder ELFDATA2LSB
-#else
-# error "Unknown BYTE_ORDER " BYTE_ORDER
-# define byteorder ELFDATANONE
-#endif
-
-#define STRING(x) __STRING (x)
-
-
-int __stack_prot attribute_hidden attribute_relro
-#if _STACK_GROWS_DOWN && defined PROT_GROWSDOWN
- = PROT_GROWSDOWN;
-#elif _STACK_GROWS_UP && defined PROT_GROWSUP
- = PROT_GROWSUP;
-#else
- = 0;
-#endif
-
-
-/* Type for the buffer we put the ELF header and hopefully the program
- header. This buffer does not really have to be too large. In most
- cases the program header follows the ELF header directly. If this
- is not the case all bets are off and we can make the header
- arbitrarily large and still won't get it read. This means the only
- question is how large are the ELF and program header combined. The
- ELF header 32-bit files is 52 bytes long and in 64-bit files is 64
- bytes long. Each program header entry is again 32 and 56 bytes
- long respectively. I.e., even with a file which has 10 program
- header entries we only have to read 372B/624B respectively. Add to
- this a bit of margin for program notes and reading 512B and 832B
- for 32-bit and 64-bit files respecitvely is enough. If this
- heuristic should really fail for some file the code in
- `_dl_map_object_from_fd' knows how to recover. */
-struct filebuf
-{
- ssize_t len;
-#if __WORDSIZE == 32
-# define FILEBUF_SIZE 512
-#else
-# define FILEBUF_SIZE 832
-#endif
- char buf[FILEBUF_SIZE] __attribute__ ((aligned (__alignof (ElfW(Ehdr)))));
-};
-
-/* This is the decomposed LD_LIBRARY_PATH search path. */
-static struct r_search_path_struct env_path_list attribute_relro;
-
-/* List of the hardware capabilities we might end up using. */
-static const struct r_strlenpair *capstr attribute_relro;
-static size_t ncapstr attribute_relro;
-static size_t max_capstrlen attribute_relro;
-
-
-/* Get the generated information about the trusted directories. */
-#include "trusted-dirs.h"
-
-static const char system_dirs[] = SYSTEM_DIRS;
-static const size_t system_dirs_len[] =
-{
- SYSTEM_DIRS_LEN
-};
-#define nsystem_dirs_len \
- (sizeof (system_dirs_len) / sizeof (system_dirs_len[0]))
-
-
-static bool
-is_trusted_path (const char *path, size_t len)
-{
- const char *trun = system_dirs;
-
- for (size_t idx = 0; idx < nsystem_dirs_len; ++idx)
- {
- if (len == system_dirs_len[idx] && memcmp (trun, path, len) == 0)
- /* Found it. */
- return true;
-
- trun += system_dirs_len[idx] + 1;
- }
-
- return false;
-}
-
-
-static bool
-is_trusted_path_normalize (const char *path, size_t len)
-{
- if (len == 0)
- return false;
-
- if (*path == ':')
- {
- ++path;
- --len;
- }
-
- char *npath = (char *) alloca (len + 2);
- char *wnp = npath;
- while (*path != '\0')
- {
- if (path[0] == '/')
- {
- if (path[1] == '.')
- {
- if (path[2] == '.' && (path[3] == '/' || path[3] == '\0'))
- {
- while (wnp > npath && *--wnp != '/')
- ;
- path += 3;
- continue;
- }
- else if (path[2] == '/' || path[2] == '\0')
- {
- path += 2;
- continue;
- }
- }
-
- if (wnp > npath && wnp[-1] == '/')
- {
- ++path;
- continue;
- }
- }
-
- *wnp++ = *path++;
- }
-
- if (wnp == npath || wnp[-1] != '/')
- *wnp++ = '/';
-
- const char *trun = system_dirs;
-
- for (size_t idx = 0; idx < nsystem_dirs_len; ++idx)
- {
- if (wnp - npath >= system_dirs_len[idx]
- && memcmp (trun, npath, system_dirs_len[idx]) == 0)
- /* Found it. */
- return true;
-
- trun += system_dirs_len[idx] + 1;
- }
-
- return false;
-}
-
-
-static size_t
-is_dst (const char *start, const char *name, const char *str,
- int is_path, int secure)
-{
- size_t len;
- bool is_curly = false;
-
- if (name[0] == '{')
- {
- is_curly = true;
- ++name;
- }
-
- len = 0;
- while (name[len] == str[len] && name[len] != '\0')
- ++len;
-
- if (is_curly)
- {
- if (name[len] != '}')
- return 0;
-
- /* Point again at the beginning of the name. */
- --name;
- /* Skip over closing curly brace and adjust for the --name. */
- len += 2;
- }
- else if (name[len] != '\0' && name[len] != '/'
- && (!is_path || name[len] != ':'))
- return 0;
-
- if (__glibc_unlikely (secure)
- && ((name[len] != '\0' && name[len] != '/'
- && (!is_path || name[len] != ':'))
- || (name != start + 1 && (!is_path || name[-2] != ':'))))
- return 0;
-
- return len;
-}
-
-
-size_t
-_dl_dst_count (const char *name, int is_path)
-{
- const char *const start = name;
- size_t cnt = 0;
-
- do
- {
- size_t len;
-
- /* $ORIGIN is not expanded for SUID/GUID programs (except if it
- is $ORIGIN alone) and it must always appear first in path. */
- ++name;
- if ((len = is_dst (start, name, "ORIGIN", is_path,
- __libc_enable_secure)) != 0
- || (len = is_dst (start, name, "PLATFORM", is_path, 0)) != 0
- || (len = is_dst (start, name, "LIB", is_path, 0)) != 0)
- ++cnt;
-
- name = strchr (name + len, '$');
- }
- while (name != NULL);
-
- return cnt;
-}
-
-
-char *
-_dl_dst_substitute (struct link_map *l, const char *name, char *result,
- int is_path)
-{
- const char *const start = name;
-
- /* Now fill the result path. While copying over the string we keep
- track of the start of the last path element. When we come across
- a DST we copy over the value or (if the value is not available)
- leave the entire path element out. */
- char *wp = result;
- char *last_elem = result;
- bool check_for_trusted = false;
-
- do
- {
- if (__glibc_unlikely (*name == '$'))
- {
- const char *repl = NULL;
- size_t len;
-
- ++name;
- if ((len = is_dst (start, name, "ORIGIN", is_path,
- __libc_enable_secure)) != 0)
- {
- repl = l->l_origin;
- check_for_trusted = (__libc_enable_secure
- && l->l_type == lt_executable);
- }
- else if ((len = is_dst (start, name, "PLATFORM", is_path, 0)) != 0)
- repl = GLRO(dl_platform);
- else if ((len = is_dst (start, name, "LIB", is_path, 0)) != 0)
- repl = DL_DST_LIB;
-
- if (repl != NULL && repl != (const char *) -1)
- {
- wp = __stpcpy (wp, repl);
- name += len;
- }
- else if (len > 1)
- {
- /* We cannot use this path element, the value of the
- replacement is unknown. */
- wp = last_elem;
- name += len;
- while (*name != '\0' && (!is_path || *name != ':'))
- ++name;
- /* Also skip following colon if this is the first rpath
- element, but keep an empty element at the end. */
- if (wp == result && is_path && *name == ':' && name[1] != '\0')
- ++name;
- }
- else
- /* No DST we recognize. */
- *wp++ = '$';
- }
- else
- {
- *wp++ = *name++;
- if (is_path && *name == ':')
- {
- /* In SUID/SGID programs, after $ORIGIN expansion the
- normalized path must be rooted in one of the trusted
- directories. */
- if (__glibc_unlikely (check_for_trusted)
- && !is_trusted_path_normalize (last_elem, wp - last_elem))
- wp = last_elem;
- else
- last_elem = wp;
-
- check_for_trusted = false;
- }
- }
- }
- while (*name != '\0');
-
- /* In SUID/SGID programs, after $ORIGIN expansion the normalized
- path must be rooted in one of the trusted directories. */
- if (__glibc_unlikely (check_for_trusted)
- && !is_trusted_path_normalize (last_elem, wp - last_elem))
- wp = last_elem;
-
- *wp = '\0';
-
- return result;
-}
-
-
-/* Return copy of argument with all recognized dynamic string tokens
- ($ORIGIN and $PLATFORM for now) replaced. On some platforms it
- might not be possible to determine the path from which the object
- belonging to the map is loaded. In this case the path element
- containing $ORIGIN is left out. */
-static char *
-expand_dynamic_string_token (struct link_map *l, const char *s, int is_path)
-{
- /* We make two runs over the string. First we determine how large the
- resulting string is and then we copy it over. Since this is no
- frequently executed operation we are looking here not for performance
- but rather for code size. */
- size_t cnt;
- size_t total;
- char *result;
-
- /* Determine the number of DST elements. */
- cnt = DL_DST_COUNT (s, is_path);
-
- /* If we do not have to replace anything simply copy the string. */
- if (__glibc_likely (cnt == 0))
- return __strdup (s);
-
- /* Determine the length of the substituted string. */
- total = DL_DST_REQUIRED (l, s, strlen (s), cnt);
-
- /* Allocate the necessary memory. */
- result = (char *) malloc (total + 1);
- if (result == NULL)
- return NULL;
-
- return _dl_dst_substitute (l, s, result, is_path);
-}
-
-
-/* Add `name' to the list of names for a particular shared object.
- `name' is expected to have been allocated with malloc and will
- be freed if the shared object already has this name.
- Returns false if the object already had this name. */
-static void
-internal_function
-add_name_to_object (struct link_map *l, const char *name)
-{
- struct libname_list *lnp, *lastp;
- struct libname_list *newname;
- size_t name_len;
-
- lastp = NULL;
- for (lnp = l->l_libname; lnp != NULL; lastp = lnp, lnp = lnp->next)
- if (strcmp (name, lnp->name) == 0)
- return;
-
- name_len = strlen (name) + 1;
- newname = (struct libname_list *) malloc (sizeof *newname + name_len);
- if (newname == NULL)
- {
- /* No more memory. */
- _dl_signal_error (ENOMEM, name, NULL, N_("cannot allocate name record"));
- return;
- }
- /* The object should have a libname set from _dl_new_object. */
- assert (lastp != NULL);
-
- newname->name = memcpy (newname + 1, name, name_len);
- newname->next = NULL;
- newname->dont_free = 0;
- lastp->next = newname;
-}
-
-/* Standard search directories. */
-static struct r_search_path_struct rtld_search_dirs attribute_relro;
-
-static size_t max_dirnamelen;
-
-static struct r_search_path_elem **
-fillin_rpath (char *rpath, struct r_search_path_elem **result, const char *sep,
- int check_trusted, const char *what, const char *where,
- struct link_map *l)
-{
- char *cp;
- size_t nelems = 0;
- char *to_free;
-
- while ((cp = __strsep (&rpath, sep)) != NULL)
- {
- struct r_search_path_elem *dirp;
-
- to_free = cp = expand_dynamic_string_token (l, cp, 1);
-
- size_t len = strlen (cp);
-
- /* `strsep' can pass an empty string. This has to be
- interpreted as `use the current directory'. */
- if (len == 0)
- {
- static const char curwd[] = "./";
- cp = (char *) curwd;
- }
-
- /* Remove trailing slashes (except for "/"). */
- while (len > 1 && cp[len - 1] == '/')
- --len;
-
- /* Now add one if there is none so far. */
- if (len > 0 && cp[len - 1] != '/')
- cp[len++] = '/';
-
- /* Make sure we don't use untrusted directories if we run SUID. */
- if (__glibc_unlikely (check_trusted) && !is_trusted_path (cp, len))
- {
- free (to_free);
- continue;
- }
-
- /* See if this directory is already known. */
- for (dirp = GL(dl_all_dirs); dirp != NULL; dirp = dirp->next)
- if (dirp->dirnamelen == len && memcmp (cp, dirp->dirname, len) == 0)
- break;
-
- if (dirp != NULL)
- {
- /* It is available, see whether it's on our own list. */
- size_t cnt;
- for (cnt = 0; cnt < nelems; ++cnt)
- if (result[cnt] == dirp)
- break;
-
- if (cnt == nelems)
- result[nelems++] = dirp;
- }
- else
- {
- size_t cnt;
- enum r_dir_status init_val;
- size_t where_len = where ? strlen (where) + 1 : 0;
-
- /* It's a new directory. Create an entry and add it. */
- dirp = (struct r_search_path_elem *)
- malloc (sizeof (*dirp) + ncapstr * sizeof (enum r_dir_status)
- + where_len + len + 1);
- if (dirp == NULL)
- _dl_signal_error (ENOMEM, NULL, NULL,
- N_("cannot create cache for search path"));
-
- dirp->dirname = ((char *) dirp + sizeof (*dirp)
- + ncapstr * sizeof (enum r_dir_status));
- *((char *) __mempcpy ((char *) dirp->dirname, cp, len)) = '\0';
- dirp->dirnamelen = len;
-
- if (len > max_dirnamelen)
- max_dirnamelen = len;
-
- /* We have to make sure all the relative directories are
- never ignored. The current directory might change and
- all our saved information would be void. */
- init_val = cp[0] != '/' ? existing : unknown;
- for (cnt = 0; cnt < ncapstr; ++cnt)
- dirp->status[cnt] = init_val;
-
- dirp->what = what;
- if (__glibc_likely (where != NULL))
- dirp->where = memcpy ((char *) dirp + sizeof (*dirp) + len + 1
- + (ncapstr * sizeof (enum r_dir_status)),
- where, where_len);
- else
- dirp->where = NULL;
-
- dirp->next = GL(dl_all_dirs);
- GL(dl_all_dirs) = dirp;
-
- /* Put it in the result array. */
- result[nelems++] = dirp;
- }
- free (to_free);
- }
-
- /* Terminate the array. */
- result[nelems] = NULL;
-
- return result;
-}
-
-
-static bool
-internal_function
-decompose_rpath (struct r_search_path_struct *sps,
- const char *rpath, struct link_map *l, const char *what)
-{
- /* Make a copy we can work with. */
- const char *where = l->l_name;
- char *copy;
- char *cp;
- struct r_search_path_elem **result;
- size_t nelems;
- /* Initialize to please the compiler. */
- const char *errstring = NULL;
-
- /* First see whether we must forget the RUNPATH and RPATH from this
- object. */
- if (__glibc_unlikely (GLRO(dl_inhibit_rpath) != NULL)
- && !__libc_enable_secure)
- {
- const char *inhp = GLRO(dl_inhibit_rpath);
-
- do
- {
- const char *wp = where;
-
- while (*inhp == *wp && *wp != '\0')
- {
- ++inhp;
- ++wp;
- }
-
- if (*wp == '\0' && (*inhp == '\0' || *inhp == ':'))
- {
- /* This object is on the list of objects for which the
- RUNPATH and RPATH must not be used. */
- sps->dirs = (void *) -1;
- return false;
- }
-
- while (*inhp != '\0')
- if (*inhp++ == ':')
- break;
- }
- while (*inhp != '\0');
- }
-
- /* Make a writable copy. */
- copy = __strdup (rpath);
- if (copy == NULL)
- {
- errstring = N_("cannot create RUNPATH/RPATH copy");
- goto signal_error;
- }
-
- /* Ignore empty rpaths. */
- if (*copy == 0)
- {
- free (copy);
- sps->dirs = (struct r_search_path_elem **) -1;
- return false;
- }
-
- /* Count the number of necessary elements in the result array. */
- nelems = 0;
- for (cp = copy; *cp != '\0'; ++cp)
- if (*cp == ':')
- ++nelems;
-
- /* Allocate room for the result. NELEMS + 1 is an upper limit for the
- number of necessary entries. */
- result = (struct r_search_path_elem **) malloc ((nelems + 1 + 1)
- * sizeof (*result));
- if (result == NULL)
- {
- free (copy);
- errstring = N_("cannot create cache for search path");
- signal_error:
- _dl_signal_error (ENOMEM, NULL, NULL, errstring);
- }
-
- fillin_rpath (copy, result, ":", 0, what, where, l);
-
- /* Free the copied RPATH string. `fillin_rpath' make own copies if
- necessary. */
- free (copy);
-
- sps->dirs = result;
- /* The caller will change this value if we haven't used a real malloc. */
- sps->malloced = 1;
- return true;
-}
-
-/* Make sure cached path information is stored in *SP
- and return true if there are any paths to search there. */
-static bool
-cache_rpath (struct link_map *l,
- struct r_search_path_struct *sp,
- int tag,
- const char *what)
-{
- if (sp->dirs == (void *) -1)
- return false;
-
- if (sp->dirs != NULL)
- return true;
-
- if (l->l_info[tag] == NULL)
- {
- /* There is no path. */
- sp->dirs = (void *) -1;
- return false;
- }
-
- /* Make sure the cache information is available. */
- return decompose_rpath (sp, (const char *) (D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[tag]->d_un.d_val),
- l, what);
-}
-
-
-void
-internal_function
-_dl_init_paths (const char *llp)
-{
- size_t idx;
- const char *strp;
- struct r_search_path_elem *pelem, **aelem;
- size_t round_size;
- struct link_map __attribute__ ((unused)) *l = NULL;
- /* Initialize to please the compiler. */
- const char *errstring = NULL;
-
- /* Fill in the information about the application's RPATH and the
- directories addressed by the LD_LIBRARY_PATH environment variable. */
-
- /* Get the capabilities. */
- capstr = _dl_important_hwcaps (GLRO(dl_platform), GLRO(dl_platformlen),
- &ncapstr, &max_capstrlen);
-
- /* First set up the rest of the default search directory entries. */
- aelem = rtld_search_dirs.dirs = (struct r_search_path_elem **)
- malloc ((nsystem_dirs_len + 1) * sizeof (struct r_search_path_elem *));
- if (rtld_search_dirs.dirs == NULL)
- {
- errstring = N_("cannot create search path array");
- signal_error:
- _dl_signal_error (ENOMEM, NULL, NULL, errstring);
- }
-
- round_size = ((2 * sizeof (struct r_search_path_elem) - 1
- + ncapstr * sizeof (enum r_dir_status))
- / sizeof (struct r_search_path_elem));
-
- rtld_search_dirs.dirs[0] = (struct r_search_path_elem *)
- malloc ((sizeof (system_dirs) / sizeof (system_dirs[0]))
- * round_size * sizeof (struct r_search_path_elem));
- if (rtld_search_dirs.dirs[0] == NULL)
- {
- errstring = N_("cannot create cache for search path");
- goto signal_error;
- }
-
- rtld_search_dirs.malloced = 0;
- pelem = GL(dl_all_dirs) = rtld_search_dirs.dirs[0];
- strp = system_dirs;
- idx = 0;
-
- do
- {
- size_t cnt;
-
- *aelem++ = pelem;
-
- pelem->what = "system search path";
- pelem->where = NULL;
-
- pelem->dirname = strp;
- pelem->dirnamelen = system_dirs_len[idx];
- strp += system_dirs_len[idx] + 1;
-
- /* System paths must be absolute. */
- assert (pelem->dirname[0] == '/');
- for (cnt = 0; cnt < ncapstr; ++cnt)
- pelem->status[cnt] = unknown;
-
- pelem->next = (++idx == nsystem_dirs_len ? NULL : (pelem + round_size));
-
- pelem += round_size;
- }
- while (idx < nsystem_dirs_len);
-
- max_dirnamelen = SYSTEM_DIRS_MAX_LEN;
- *aelem = NULL;
-
-#ifdef SHARED
- /* This points to the map of the main object. */
- l = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
- if (l != NULL)
- {
- assert (l->l_type != lt_loaded);
-
- if (l->l_info[DT_RUNPATH])
- {
- /* Allocate room for the search path and fill in information
- from RUNPATH. */
- decompose_rpath (&l->l_runpath_dirs,
- (const void *) (D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[DT_RUNPATH]->d_un.d_val),
- l, "RUNPATH");
- /* During rtld init the memory is allocated by the stub malloc,
- prevent any attempt to free it by the normal malloc. */
- l->l_runpath_dirs.malloced = 0;
-
- /* The RPATH is ignored. */
- l->l_rpath_dirs.dirs = (void *) -1;
- }
- else
- {
- l->l_runpath_dirs.dirs = (void *) -1;
-
- if (l->l_info[DT_RPATH])
- {
- /* Allocate room for the search path and fill in information
- from RPATH. */
- decompose_rpath (&l->l_rpath_dirs,
- (const void *) (D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[DT_RPATH]->d_un.d_val),
- l, "RPATH");
- /* During rtld init the memory is allocated by the stub
- malloc, prevent any attempt to free it by the normal
- malloc. */
- l->l_rpath_dirs.malloced = 0;
- }
- else
- l->l_rpath_dirs.dirs = (void *) -1;
- }
- }
-#endif /* SHARED */
-
- if (llp != NULL && *llp != '\0')
- {
- size_t nllp;
- const char *cp = llp;
- char *llp_tmp;
-
-#ifdef SHARED
- /* Expand DSTs. */
- size_t cnt = DL_DST_COUNT (llp, 1);
- if (__glibc_likely (cnt == 0))
- llp_tmp = strdupa (llp);
- else
- {
- /* Determine the length of the substituted string. */
- size_t total = DL_DST_REQUIRED (l, llp, strlen (llp), cnt);
-
- /* Allocate the necessary memory. */
- llp_tmp = (char *) alloca (total + 1);
- llp_tmp = _dl_dst_substitute (l, llp, llp_tmp, 1);
- }
-#else
- llp_tmp = strdupa (llp);
-#endif
-
- /* Decompose the LD_LIBRARY_PATH contents. First determine how many
- elements it has. */
- nllp = 1;
- while (*cp)
- {
- if (*cp == ':' || *cp == ';')
- ++nllp;
- ++cp;
- }
-
- env_path_list.dirs = (struct r_search_path_elem **)
- malloc ((nllp + 1) * sizeof (struct r_search_path_elem *));
- if (env_path_list.dirs == NULL)
- {
- errstring = N_("cannot create cache for search path");
- goto signal_error;
- }
-
- (void) fillin_rpath (llp_tmp, env_path_list.dirs, ":;",
- __libc_enable_secure, "LD_LIBRARY_PATH",
- NULL, l);
-
- if (env_path_list.dirs[0] == NULL)
- {
- free (env_path_list.dirs);
- env_path_list.dirs = (void *) -1;
- }
-
- env_path_list.malloced = 0;
- }
- else
- env_path_list.dirs = (void *) -1;
-}
-
-
-static void
-__attribute__ ((noreturn, noinline))
-lose (int code, int fd, const char *name, char *realname, struct link_map *l,
- const char *msg, struct r_debug *r, Lmid_t nsid)
-{
- /* The file might already be closed. */
- if (fd != -1)
- (void) __close (fd);
- if (l != NULL && l->l_origin != (char *) -1l)
- free ((char *) l->l_origin);
- free (l);
- free (realname);
-
- if (r != NULL)
- {
- r->r_state = RT_CONSISTENT;
- _dl_debug_state ();
- LIBC_PROBE (map_failed, 2, nsid, r);
- }
-
- _dl_signal_error (code, name, NULL, msg);
-}
-
-
-/* Map in the shared object NAME, actually located in REALNAME, and already
- opened on FD. */
-
-#ifndef EXTERNAL_MAP_FROM_FD
-static
-#endif
-struct link_map *
-_dl_map_object_from_fd (const char *name, const char *origname, int fd,
- struct filebuf *fbp, char *realname,
- struct link_map *loader, int l_type, int mode,
- void **stack_endp, Lmid_t nsid)
-{
- struct link_map *l = NULL;
- const ElfW(Ehdr) *header;
- const ElfW(Phdr) *phdr;
- const ElfW(Phdr) *ph;
- size_t maplength;
- int type;
- /* Initialize to keep the compiler happy. */
- const char *errstring = NULL;
- int errval = 0;
- struct r_debug *r = _dl_debug_initialize (0, nsid);
- bool make_consistent = false;
-
- /* Get file information. */
- struct r_file_id id;
- if (__glibc_unlikely (!_dl_get_file_id (fd, &id)))
- {
- errstring = N_("cannot stat shared object");
- call_lose_errno:
- errval = errno;
- call_lose:
- lose (errval, fd, name, realname, l, errstring,
- make_consistent ? r : NULL, nsid);
- }
-
- /* Look again to see if the real name matched another already loaded. */
- for (l = GL(dl_ns)[nsid]._ns_loaded; l != NULL; l = l->l_next)
- if (!l->l_removed && _dl_file_id_match_p (&l->l_file_id, &id))
- {
- /* The object is already loaded.
- Just bump its reference count and return it. */
- __close (fd);
-
- /* If the name is not in the list of names for this object add
- it. */
- free (realname);
- add_name_to_object (l, name);
-
- return l;
- }
-
-#ifdef SHARED
- /* When loading into a namespace other than the base one we must
- avoid loading ld.so since there can only be one copy. Ever. */
- if (__glibc_unlikely (nsid != LM_ID_BASE)
- && (_dl_file_id_match_p (&id, &GL(dl_rtld_map).l_file_id)
- || _dl_name_match_p (name, &GL(dl_rtld_map))))
- {
- /* This is indeed ld.so. Create a new link_map which refers to
- the real one for almost everything. */
- l = _dl_new_object (realname, name, l_type, loader, mode, nsid);
- if (l == NULL)
- goto fail_new;
-
- /* Refer to the real descriptor. */
- l->l_real = &GL(dl_rtld_map);
-
- /* No need to bump the refcount of the real object, ld.so will
- never be unloaded. */
- __close (fd);
-
- /* Add the map for the mirrored object to the object list. */
- _dl_add_to_namespace_list (l, nsid);
-
- return l;
- }
-#endif
-
- if (mode & RTLD_NOLOAD)
- {
- /* We are not supposed to load the object unless it is already
- loaded. So return now. */
- free (realname);
- __close (fd);
- return NULL;
- }
-
- /* Print debugging message. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("file=%s [%lu]; generating link map\n", name, nsid);
-
- /* This is the ELF header. We read it in `open_verify'. */
- header = (void *) fbp->buf;
-
-#ifndef MAP_ANON
-# define MAP_ANON 0
- if (_dl_zerofd == -1)
- {
- _dl_zerofd = _dl_sysdep_open_zero_fill ();
- if (_dl_zerofd == -1)
- {
- free (realname);
- __close (fd);
- _dl_signal_error (errno, NULL, NULL,
- N_("cannot open zero fill device"));
- }
- }
-#endif
-
- /* Signal that we are going to add new objects. */
- if (r->r_state == RT_CONSISTENT)
- {
-#ifdef SHARED
- /* Auditing checkpoint: we are going to add new objects. */
- if ((mode & __RTLD_AUDIT) == 0
- && __glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- struct link_map *head = GL(dl_ns)[nsid]._ns_loaded;
- /* Do not call the functions for any auditing object. */
- if (head->l_auditing == 0)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&head->l_audit[cnt].cookie, LA_ACT_ADD);
-
- afct = afct->next;
- }
- }
- }
-#endif
-
- /* Notify the debugger we have added some objects. We need to
- call _dl_debug_initialize in a static program in case dynamic
- linking has not been used before. */
- r->r_state = RT_ADD;
- _dl_debug_state ();
- LIBC_PROBE (map_start, 2, nsid, r);
- make_consistent = true;
- }
- else
- assert (r->r_state == RT_ADD);
-
- /* Enter the new object in the list of loaded objects. */
- l = _dl_new_object (realname, name, l_type, loader, mode, nsid);
- if (__glibc_unlikely (l == NULL))
- {
-#ifdef SHARED
- fail_new:
-#endif
- errstring = N_("cannot create shared object descriptor");
- goto call_lose_errno;
- }
-
- /* Extract the remaining details we need from the ELF header
- and then read in the program header table. */
- l->l_entry = header->e_entry;
- type = header->e_type;
- l->l_phnum = header->e_phnum;
-
- maplength = header->e_phnum * sizeof (ElfW(Phdr));
- if (header->e_phoff + maplength <= (size_t) fbp->len)
- phdr = (void *) (fbp->buf + header->e_phoff);
- else
- {
- phdr = alloca (maplength);
- __lseek (fd, header->e_phoff, SEEK_SET);
- if ((size_t) __libc_read (fd, (void *) phdr, maplength) != maplength)
- {
- errstring = N_("cannot read file data");
- goto call_lose_errno;
- }
- }
-
- /* On most platforms presume that PT_GNU_STACK is absent and the stack is
- * executable. Other platforms default to a nonexecutable stack and don't
- * need PT_GNU_STACK to do so. */
- uint_fast16_t stack_flags = DEFAULT_STACK_PERMS;
-
- {
- /* Scan the program header table, collecting its load commands. */
- struct loadcmd loadcmds[l->l_phnum];
- size_t nloadcmds = 0;
- bool has_holes = false;
-
- /* The struct is initialized to zero so this is not necessary:
- l->l_ld = 0;
- l->l_phdr = 0;
- l->l_addr = 0; */
- for (ph = phdr; ph < &phdr[l->l_phnum]; ++ph)
- switch (ph->p_type)
- {
- /* These entries tell us where to find things once the file's
- segments are mapped in. We record the addresses it says
- verbatim, and later correct for the run-time load address. */
- case PT_DYNAMIC:
- l->l_ld = (void *) ph->p_vaddr;
- l->l_ldnum = ph->p_memsz / sizeof (ElfW(Dyn));
- break;
-
- case PT_PHDR:
- l->l_phdr = (void *) ph->p_vaddr;
- break;
-
- case PT_LOAD:
- /* A load command tells us to map in part of the file.
- We record the load commands and process them all later. */
- if (__glibc_unlikely ((ph->p_align & (GLRO(dl_pagesize) - 1)) != 0))
- {
- errstring = N_("ELF load command alignment not page-aligned");
- goto call_lose;
- }
- if (__glibc_unlikely (((ph->p_vaddr - ph->p_offset)
- & (ph->p_align - 1)) != 0))
- {
- errstring
- = N_("ELF load command address/offset not properly aligned");
- goto call_lose;
- }
-
- struct loadcmd *c = &loadcmds[nloadcmds++];
- c->mapstart = ALIGN_DOWN (ph->p_vaddr, GLRO(dl_pagesize));
- c->mapend = ALIGN_UP (ph->p_vaddr + ph->p_filesz, GLRO(dl_pagesize));
- c->dataend = ph->p_vaddr + ph->p_filesz;
- c->allocend = ph->p_vaddr + ph->p_memsz;
- c->mapoff = ALIGN_DOWN (ph->p_offset, GLRO(dl_pagesize));
-
- /* Determine whether there is a gap between the last segment
- and this one. */
- if (nloadcmds > 1 && c[-1].mapend != c->mapstart)
- has_holes = true;
-
- /* Optimize a common case. */
-#if (PF_R | PF_W | PF_X) == 7 && (PROT_READ | PROT_WRITE | PROT_EXEC) == 7
- c->prot = (PF_TO_PROT
- >> ((ph->p_flags & (PF_R | PF_W | PF_X)) * 4)) & 0xf;
-#else
- c->prot = 0;
- if (ph->p_flags & PF_R)
- c->prot |= PROT_READ;
- if (ph->p_flags & PF_W)
- c->prot |= PROT_WRITE;
- if (ph->p_flags & PF_X)
- c->prot |= PROT_EXEC;
-#endif
- break;
-
- case PT_TLS:
- if (ph->p_memsz == 0)
- /* Nothing to do for an empty segment. */
- break;
-
- l->l_tls_blocksize = ph->p_memsz;
- l->l_tls_align = ph->p_align;
- if (ph->p_align == 0)
- l->l_tls_firstbyte_offset = 0;
- else
- l->l_tls_firstbyte_offset = ph->p_vaddr & (ph->p_align - 1);
- l->l_tls_initimage_size = ph->p_filesz;
- /* Since we don't know the load address yet only store the
- offset. We will adjust it later. */
- l->l_tls_initimage = (void *) ph->p_vaddr;
-
- /* If not loading the initial set of shared libraries,
- check whether we should permit loading a TLS segment. */
- if (__glibc_likely (l->l_type == lt_library)
- /* If GL(dl_tls_dtv_slotinfo_list) == NULL, then rtld.c did
- not set up TLS data structures, so don't use them now. */
- || __glibc_likely (GL(dl_tls_dtv_slotinfo_list) != NULL))
- {
- /* Assign the next available module ID. */
- l->l_tls_modid = _dl_next_tls_modid ();
- break;
- }
-
-#ifdef SHARED
- /* We are loading the executable itself when the dynamic
- linker was executed directly. The setup will happen
- later. Otherwise, the TLS data structures are already
- initialized, and we assigned a TLS modid above. */
- assert (l->l_prev == NULL || (mode & __RTLD_AUDIT) != 0);
-#else
- assert (false && "TLS not initialized in static application");
-#endif
- break;
-
- case PT_GNU_STACK:
- stack_flags = ph->p_flags;
- break;
-
- case PT_GNU_RELRO:
- l->l_relro_addr = ph->p_vaddr;
- l->l_relro_size = ph->p_memsz;
- break;
- }
-
- if (__glibc_unlikely (nloadcmds == 0))
- {
- /* This only happens for a bogus object that will be caught with
- another error below. But we don't want to go through the
- calculations below using NLOADCMDS - 1. */
- errstring = N_("object file has no loadable segments");
- goto call_lose;
- }
-
- if (__glibc_unlikely (type != ET_DYN)
- && __glibc_unlikely ((mode & __RTLD_OPENEXEC) == 0))
- {
- /* This object is loaded at a fixed address. This must never
- happen for objects loaded with dlopen. */
- errstring = N_("cannot dynamically load executable");
- goto call_lose;
- }
-
- /* Length of the sections to be loaded. */
- maplength = loadcmds[nloadcmds - 1].allocend - loadcmds[0].mapstart;
-
- /* Now process the load commands and map segments into memory.
- This is responsible for filling in:
- l_map_start, l_map_end, l_addr, l_contiguous, l_text_end, l_phdr
- */
- errstring = _dl_map_segments (l, fd, header, type, loadcmds, nloadcmds,
- maplength, has_holes, loader);
- if (__glibc_unlikely (errstring != NULL))
- goto call_lose;
- }
-
- if (l->l_ld == 0)
- {
- if (__glibc_unlikely (type == ET_DYN))
- {
- errstring = N_("object file has no dynamic section");
- goto call_lose;
- }
- }
- else
- l->l_ld = (ElfW(Dyn) *) ((ElfW(Addr)) l->l_ld + l->l_addr);
-
- elf_get_dynamic_info (l, NULL);
-
- /* Make sure we are not dlopen'ing an object that has the
- DF_1_NOOPEN flag set. */
- if (__glibc_unlikely (l->l_flags_1 & DF_1_NOOPEN)
- && (mode & __RTLD_DLOPEN))
- {
- /* We are not supposed to load this object. Free all resources. */
- _dl_unmap_segments (l);
-
- if (!l->l_libname->dont_free)
- free (l->l_libname);
-
- if (l->l_phdr_allocated)
- free ((void *) l->l_phdr);
-
- errstring = N_("shared object cannot be dlopen()ed");
- goto call_lose;
- }
-
- if (l->l_phdr == NULL)
- {
- /* The program header is not contained in any of the segments.
- We have to allocate memory ourself and copy it over from out
- temporary place. */
- ElfW(Phdr) *newp = (ElfW(Phdr) *) malloc (header->e_phnum
- * sizeof (ElfW(Phdr)));
- if (newp == NULL)
- {
- errstring = N_("cannot allocate memory for program header");
- goto call_lose_errno;
- }
-
- l->l_phdr = memcpy (newp, phdr,
- (header->e_phnum * sizeof (ElfW(Phdr))));
- l->l_phdr_allocated = 1;
- }
- else
- /* Adjust the PT_PHDR value by the runtime load address. */
- l->l_phdr = (ElfW(Phdr) *) ((ElfW(Addr)) l->l_phdr + l->l_addr);
-
- if (__glibc_unlikely ((stack_flags &~ GL(dl_stack_flags)) & PF_X))
- {
- if (__glibc_unlikely (__check_caller (RETURN_ADDRESS (0), allow_ldso) != 0))
- {
- errstring = N_("invalid caller");
- goto call_lose;
- }
-
- /* The stack is presently not executable, but this module
- requires that it be executable. We must change the
- protection of the variable which contains the flags used in
- the mprotect calls. */
-#ifdef SHARED
- if ((mode & (__RTLD_DLOPEN | __RTLD_AUDIT)) == __RTLD_DLOPEN)
- {
- const uintptr_t p = (uintptr_t) &__stack_prot & -GLRO(dl_pagesize);
- const size_t s = (uintptr_t) (&__stack_prot + 1) - p;
-
- struct link_map *const m = &GL(dl_rtld_map);
- const uintptr_t relro_end = ((m->l_addr + m->l_relro_addr
- + m->l_relro_size)
- & -GLRO(dl_pagesize));
- if (__glibc_likely (p + s <= relro_end))
- {
- /* The variable lies in the region protected by RELRO. */
- if (__mprotect ((void *) p, s, PROT_READ|PROT_WRITE) < 0)
- {
- errstring = N_("cannot change memory protections");
- goto call_lose_errno;
- }
- __stack_prot |= PROT_READ|PROT_WRITE|PROT_EXEC;
- __mprotect ((void *) p, s, PROT_READ);
- }
- else
- __stack_prot |= PROT_READ|PROT_WRITE|PROT_EXEC;
- }
- else
-#endif
- __stack_prot |= PROT_READ|PROT_WRITE|PROT_EXEC;
-
-#ifdef check_consistency
- check_consistency ();
-#endif
-
- errval = (*GL(dl_make_stack_executable_hook)) (stack_endp);
- if (errval)
- {
- errstring = N_("\
-cannot enable executable stack as shared object requires");
- goto call_lose;
- }
- }
-
- /* Adjust the address of the TLS initialization image. */
- if (l->l_tls_initimage != NULL)
- l->l_tls_initimage = (char *) l->l_tls_initimage + l->l_addr;
-
- /* We are done mapping in the file. We no longer need the descriptor. */
- if (__glibc_unlikely (__close (fd) != 0))
- {
- errstring = N_("cannot close file descriptor");
- goto call_lose_errno;
- }
- /* Signal that we closed the file. */
- fd = -1;
-
- /* If this is ET_EXEC, we should have loaded it as lt_executable. */
- assert (type != ET_EXEC || l->l_type == lt_executable);
-
- l->l_entry += l->l_addr;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("\
- dynamic: 0x%0*lx base: 0x%0*lx size: 0x%0*Zx\n\
- entry: 0x%0*lx phdr: 0x%0*lx phnum: %*u\n\n",
- (int) sizeof (void *) * 2,
- (unsigned long int) l->l_ld,
- (int) sizeof (void *) * 2,
- (unsigned long int) l->l_addr,
- (int) sizeof (void *) * 2, maplength,
- (int) sizeof (void *) * 2,
- (unsigned long int) l->l_entry,
- (int) sizeof (void *) * 2,
- (unsigned long int) l->l_phdr,
- (int) sizeof (void *) * 2, l->l_phnum);
-
- /* Set up the symbol hash table. */
- _dl_setup_hash (l);
-
- /* If this object has DT_SYMBOLIC set modify now its scope. We don't
- have to do this for the main map. */
- if ((mode & RTLD_DEEPBIND) == 0
- && __glibc_unlikely (l->l_info[DT_SYMBOLIC] != NULL)
- && &l->l_searchlist != l->l_scope[0])
- {
- /* Create an appropriate searchlist. It contains only this map.
- This is the definition of DT_SYMBOLIC in SysVr4. */
- l->l_symbolic_searchlist.r_list[0] = l;
- l->l_symbolic_searchlist.r_nlist = 1;
-
- /* Now move the existing entries one back. */
- memmove (&l->l_scope[1], &l->l_scope[0],
- (l->l_scope_max - 1) * sizeof (l->l_scope[0]));
-
- /* Now add the new entry. */
- l->l_scope[0] = &l->l_symbolic_searchlist;
- }
-
- /* Remember whether this object must be initialized first. */
- if (l->l_flags_1 & DF_1_INITFIRST)
- GL(dl_initfirst) = l;
-
- /* Finally the file information. */
- l->l_file_id = id;
-
-#ifdef SHARED
- /* When auditing is used the recorded names might not include the
- name by which the DSO is actually known. Add that as well. */
- if (__glibc_unlikely (origname != NULL))
- add_name_to_object (l, origname);
-#else
- /* Audit modules only exist when linking is dynamic so ORIGNAME
- cannot be non-NULL. */
- assert (origname == NULL);
-#endif
-
- /* When we profile the SONAME might be needed for something else but
- loading. Add it right away. */
- if (__glibc_unlikely (GLRO(dl_profile) != NULL)
- && l->l_info[DT_SONAME] != NULL)
- add_name_to_object (l, ((const char *) D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[DT_SONAME]->d_un.d_val));
-
-#ifdef DL_AFTER_LOAD
- DL_AFTER_LOAD (l);
-#endif
-
- /* Now that the object is fully initialized add it to the object list. */
- _dl_add_to_namespace_list (l, nsid);
-
-#ifdef SHARED
- /* Auditing checkpoint: we have a new object. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0)
- && !GL(dl_ns)[l->l_ns]._ns_loaded->l_auditing)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objopen != NULL)
- {
- l->l_audit[cnt].bindflags
- = afct->objopen (l, nsid, &l->l_audit[cnt].cookie);
-
- l->l_audit_any_plt |= l->l_audit[cnt].bindflags != 0;
- }
-
- afct = afct->next;
- }
- }
-#endif
-
- return l;
-}
-
-/* Print search path. */
-static void
-print_search_path (struct r_search_path_elem **list,
- const char *what, const char *name)
-{
- char buf[max_dirnamelen + max_capstrlen];
- int first = 1;
-
- _dl_debug_printf (" search path=");
-
- while (*list != NULL && (*list)->what == what) /* Yes, ==. */
- {
- char *endp = __mempcpy (buf, (*list)->dirname, (*list)->dirnamelen);
- size_t cnt;
-
- for (cnt = 0; cnt < ncapstr; ++cnt)
- if ((*list)->status[cnt] != nonexisting)
- {
- char *cp = __mempcpy (endp, capstr[cnt].str, capstr[cnt].len);
- if (cp == buf || (cp == buf + 1 && buf[0] == '/'))
- cp[0] = '\0';
- else
- cp[-1] = '\0';
-
- _dl_debug_printf_c (first ? "%s" : ":%s", buf);
- first = 0;
- }
-
- ++list;
- }
-
- if (name != NULL)
- _dl_debug_printf_c ("\t\t(%s from file %s)\n", what,
- DSO_FILENAME (name));
- else
- _dl_debug_printf_c ("\t\t(%s)\n", what);
-}
-
-/* Open a file and verify it is an ELF file for this architecture. We
- ignore only ELF files for other architectures. Non-ELF files and
- ELF files with different header information cause fatal errors since
- this could mean there is something wrong in the installation and the
- user might want to know about this.
-
- If FD is not -1, then the file is already open and FD refers to it.
- In that case, FD is consumed for both successful and error returns. */
-static int
-open_verify (const char *name, int fd,
- struct filebuf *fbp, struct link_map *loader,
- int whatcode, int mode, bool *found_other_class, bool free_name)
-{
- /* This is the expected ELF header. */
-#define ELF32_CLASS ELFCLASS32
-#define ELF64_CLASS ELFCLASS64
-#ifndef VALID_ELF_HEADER
-# define VALID_ELF_HEADER(hdr,exp,size) (memcmp (hdr, exp, size) == 0)
-# define VALID_ELF_OSABI(osabi) (osabi == ELFOSABI_SYSV)
-# define VALID_ELF_ABIVERSION(osabi,ver) (ver == 0)
-#elif defined MORE_ELF_HEADER_DATA
- MORE_ELF_HEADER_DATA;
-#endif
- static const unsigned char expected[EI_NIDENT] =
- {
- [EI_MAG0] = ELFMAG0,
- [EI_MAG1] = ELFMAG1,
- [EI_MAG2] = ELFMAG2,
- [EI_MAG3] = ELFMAG3,
- [EI_CLASS] = ELFW(CLASS),
- [EI_DATA] = byteorder,
- [EI_VERSION] = EV_CURRENT,
- [EI_OSABI] = ELFOSABI_SYSV,
- [EI_ABIVERSION] = 0
- };
- static const struct
- {
- ElfW(Word) vendorlen;
- ElfW(Word) datalen;
- ElfW(Word) type;
- char vendor[4];
- } expected_note = { 4, 16, 1, "GNU" };
- /* Initialize it to make the compiler happy. */
- const char *errstring = NULL;
- int errval = 0;
-
-#ifdef SHARED
- /* Give the auditing libraries a chance. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0) && whatcode != 0
- && loader->l_auditing == 0)
- {
- const char *original_name = name;
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objsearch != NULL)
- {
- name = afct->objsearch (name, &loader->l_audit[cnt].cookie,
- whatcode);
- if (name == NULL)
- /* Ignore the path. */
- return -1;
- }
-
- afct = afct->next;
- }
-
- if (fd != -1 && name != original_name && strcmp (name, original_name))
- {
- /* An audit library changed what we're supposed to open,
- so FD no longer matches it. */
- __close (fd);
- fd = -1;
- }
- }
-#endif
-
- if (fd == -1)
- /* Open the file. We always open files read-only. */
- fd = __open (name, O_RDONLY | O_CLOEXEC);
-
- if (fd != -1)
- {
- ElfW(Ehdr) *ehdr;
- ElfW(Phdr) *phdr, *ph;
- ElfW(Word) *abi_note;
- unsigned int osversion;
- size_t maplength;
-
- /* We successfully opened the file. Now verify it is a file
- we can use. */
- __set_errno (0);
- fbp->len = 0;
- assert (sizeof (fbp->buf) > sizeof (ElfW(Ehdr)));
- /* Read in the header. */
- do
- {
- ssize_t retlen = __libc_read (fd, fbp->buf + fbp->len,
- sizeof (fbp->buf) - fbp->len);
- if (retlen <= 0)
- break;
- fbp->len += retlen;
- }
- while (__glibc_unlikely (fbp->len < sizeof (ElfW(Ehdr))));
-
- /* This is where the ELF header is loaded. */
- ehdr = (ElfW(Ehdr) *) fbp->buf;
-
- /* Now run the tests. */
- if (__glibc_unlikely (fbp->len < (ssize_t) sizeof (ElfW(Ehdr))))
- {
- errval = errno;
- errstring = (errval == 0
- ? N_("file too short") : N_("cannot read file data"));
- call_lose:
- if (free_name)
- {
- char *realname = (char *) name;
- name = strdupa (realname);
- free (realname);
- }
- lose (errval, fd, name, NULL, NULL, errstring, NULL, 0);
- }
-
- /* See whether the ELF header is what we expect. */
- if (__glibc_unlikely (! VALID_ELF_HEADER (ehdr->e_ident, expected,
- EI_ABIVERSION)
- || !VALID_ELF_ABIVERSION (ehdr->e_ident[EI_OSABI],
- ehdr->e_ident[EI_ABIVERSION])
- || memcmp (&ehdr->e_ident[EI_PAD],
- &expected[EI_PAD],
- EI_NIDENT - EI_PAD) != 0))
- {
- /* Something is wrong. */
- const Elf32_Word *magp = (const void *) ehdr->e_ident;
- if (*magp !=
-#if BYTE_ORDER == LITTLE_ENDIAN
- ((ELFMAG0 << (EI_MAG0 * 8)) |
- (ELFMAG1 << (EI_MAG1 * 8)) |
- (ELFMAG2 << (EI_MAG2 * 8)) |
- (ELFMAG3 << (EI_MAG3 * 8)))
-#else
- ((ELFMAG0 << (EI_MAG3 * 8)) |
- (ELFMAG1 << (EI_MAG2 * 8)) |
- (ELFMAG2 << (EI_MAG1 * 8)) |
- (ELFMAG3 << (EI_MAG0 * 8)))
-#endif
- )
- errstring = N_("invalid ELF header");
- else if (ehdr->e_ident[EI_CLASS] != ELFW(CLASS))
- {
- /* This is not a fatal error. On architectures where
- 32-bit and 64-bit binaries can be run this might
- happen. */
- *found_other_class = true;
- goto close_and_out;
- }
- else if (ehdr->e_ident[EI_DATA] != byteorder)
- {
- if (BYTE_ORDER == BIG_ENDIAN)
- errstring = N_("ELF file data encoding not big-endian");
- else
- errstring = N_("ELF file data encoding not little-endian");
- }
- else if (ehdr->e_ident[EI_VERSION] != EV_CURRENT)
- errstring
- = N_("ELF file version ident does not match current one");
- /* XXX We should be able so set system specific versions which are
- allowed here. */
- else if (!VALID_ELF_OSABI (ehdr->e_ident[EI_OSABI]))
- errstring = N_("ELF file OS ABI invalid");
- else if (!VALID_ELF_ABIVERSION (ehdr->e_ident[EI_OSABI],
- ehdr->e_ident[EI_ABIVERSION]))
- errstring = N_("ELF file ABI version invalid");
- else if (memcmp (&ehdr->e_ident[EI_PAD], &expected[EI_PAD],
- EI_NIDENT - EI_PAD) != 0)
- errstring = N_("nonzero padding in e_ident");
- else
- /* Otherwise we don't know what went wrong. */
- errstring = N_("internal error");
-
- goto call_lose;
- }
-
- if (__glibc_unlikely (ehdr->e_version != EV_CURRENT))
- {
- errstring = N_("ELF file version does not match current one");
- goto call_lose;
- }
- if (! __glibc_likely (elf_machine_matches_host (ehdr)))
- goto close_and_out;
- else if (__glibc_unlikely (ehdr->e_type != ET_DYN
- && ehdr->e_type != ET_EXEC))
- {
- errstring = N_("only ET_DYN and ET_EXEC can be loaded");
- goto call_lose;
- }
- else if (__glibc_unlikely (ehdr->e_type == ET_EXEC
- && (mode & __RTLD_OPENEXEC) == 0))
- {
- /* BZ #16634. It is an error to dlopen ET_EXEC (unless
- __RTLD_OPENEXEC is explicitly set). We return error here
- so that code in _dl_map_object_from_fd does not try to set
- l_tls_modid for this module. */
-
- errstring = N_("cannot dynamically load executable");
- goto call_lose;
- }
- else if (__glibc_unlikely (ehdr->e_phentsize != sizeof (ElfW(Phdr))))
- {
- errstring = N_("ELF file's phentsize not the expected size");
- goto call_lose;
- }
-
- maplength = ehdr->e_phnum * sizeof (ElfW(Phdr));
- if (ehdr->e_phoff + maplength <= (size_t) fbp->len)
- phdr = (void *) (fbp->buf + ehdr->e_phoff);
- else
- {
- phdr = alloca (maplength);
- __lseek (fd, ehdr->e_phoff, SEEK_SET);
- if ((size_t) __libc_read (fd, (void *) phdr, maplength) != maplength)
- {
- read_error:
- errval = errno;
- errstring = N_("cannot read file data");
- goto call_lose;
- }
- }
-
- if (__glibc_unlikely (elf_machine_reject_phdr_p
- (phdr, ehdr->e_phnum, fbp->buf, fbp->len,
- loader, fd)))
- goto close_and_out;
-
- /* Check .note.ABI-tag if present. */
- for (ph = phdr; ph < &phdr[ehdr->e_phnum]; ++ph)
- if (ph->p_type == PT_NOTE && ph->p_filesz >= 32 && ph->p_align >= 4)
- {
- ElfW(Addr) size = ph->p_filesz;
-
- if (ph->p_offset + size <= (size_t) fbp->len)
- abi_note = (void *) (fbp->buf + ph->p_offset);
- else
- {
- abi_note = alloca (size);
- __lseek (fd, ph->p_offset, SEEK_SET);
- if (__libc_read (fd, (void *) abi_note, size) != size)
- goto read_error;
- }
-
- while (memcmp (abi_note, &expected_note, sizeof (expected_note)))
- {
-#define ROUND(len) (((len) + sizeof (ElfW(Word)) - 1) & -sizeof (ElfW(Word)))
- ElfW(Addr) note_size = 3 * sizeof (ElfW(Word))
- + ROUND (abi_note[0])
- + ROUND (abi_note[1]);
-
- if (size - 32 < note_size)
- {
- size = 0;
- break;
- }
- size -= note_size;
- abi_note = (void *) abi_note + note_size;
- }
-
- if (size == 0)
- continue;
-
- osversion = (abi_note[5] & 0xff) * 65536
- + (abi_note[6] & 0xff) * 256
- + (abi_note[7] & 0xff);
- if (abi_note[4] != __ABI_TAG_OS
- || (GLRO(dl_osversion) && GLRO(dl_osversion) < osversion))
- {
- close_and_out:
- __close (fd);
- __set_errno (ENOENT);
- fd = -1;
- }
-
- break;
- }
- }
-
- return fd;
-}
-
-/* Try to open NAME in one of the directories in *DIRSP.
- Return the fd, or -1. If successful, fill in *REALNAME
- with the malloc'd full directory name. If it turns out
- that none of the directories in *DIRSP exists, *DIRSP is
- replaced with (void *) -1, and the old value is free()d
- if MAY_FREE_DIRS is true. */
-
-static int
-open_path (const char *name, size_t namelen, int mode,
- struct r_search_path_struct *sps, char **realname,
- struct filebuf *fbp, struct link_map *loader, int whatcode,
- bool *found_other_class)
-{
- struct r_search_path_elem **dirs = sps->dirs;
- char *buf;
- int fd = -1;
- const char *current_what = NULL;
- int any = 0;
-
- if (__glibc_unlikely (dirs == NULL))
- /* We're called before _dl_init_paths when loading the main executable
- given on the command line when rtld is run directly. */
- return -1;
-
- buf = alloca (max_dirnamelen + max_capstrlen + namelen);
- do
- {
- struct r_search_path_elem *this_dir = *dirs;
- size_t buflen = 0;
- size_t cnt;
- char *edp;
- int here_any = 0;
- int err;
-
- /* If we are debugging the search for libraries print the path
- now if it hasn't happened now. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS)
- && current_what != this_dir->what)
- {
- current_what = this_dir->what;
- print_search_path (dirs, current_what, this_dir->where);
- }
-
- edp = (char *) __mempcpy (buf, this_dir->dirname, this_dir->dirnamelen);
- for (cnt = 0; fd == -1 && cnt < ncapstr; ++cnt)
- {
- /* Skip this directory if we know it does not exist. */
- if (this_dir->status[cnt] == nonexisting)
- continue;
-
- buflen =
- ((char *) __mempcpy (__mempcpy (edp, capstr[cnt].str,
- capstr[cnt].len),
- name, namelen)
- - buf);
-
- /* Print name we try if this is wanted. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS))
- _dl_debug_printf (" trying file=%s\n", buf);
-
- fd = open_verify (buf, -1, fbp, loader, whatcode, mode,
- found_other_class, false);
- if (this_dir->status[cnt] == unknown)
- {
- if (fd != -1)
- this_dir->status[cnt] = existing;
- /* Do not update the directory information when loading
- auditing code. We must try to disturb the program as
- little as possible. */
- else if (loader == NULL
- || GL(dl_ns)[loader->l_ns]._ns_loaded->l_auditing == 0)
- {
- /* We failed to open machine dependent library. Let's
- test whether there is any directory at all. */
- struct stat64 st;
-
- buf[buflen - namelen - 1] = '\0';
-
- if (__xstat64 (_STAT_VER, buf, &st) != 0
- || ! S_ISDIR (st.st_mode))
- /* The directory does not exist or it is no directory. */
- this_dir->status[cnt] = nonexisting;
- else
- this_dir->status[cnt] = existing;
- }
- }
-
- /* Remember whether we found any existing directory. */
- here_any |= this_dir->status[cnt] != nonexisting;
-
- if (fd != -1 && __glibc_unlikely (mode & __RTLD_SECURE)
- && __libc_enable_secure)
- {
- /* This is an extra security effort to make sure nobody can
- preload broken shared objects which are in the trusted
- directories and so exploit the bugs. */
- struct stat64 st;
-
- if (__fxstat64 (_STAT_VER, fd, &st) != 0
- || (st.st_mode & S_ISUID) == 0)
- {
- /* The shared object cannot be tested for being SUID
- or this bit is not set. In this case we must not
- use this object. */
- __close (fd);
- fd = -1;
- /* We simply ignore the file, signal this by setting
- the error value which would have been set by `open'. */
- errno = ENOENT;
- }
- }
- }
-
- if (fd != -1)
- {
- *realname = (char *) malloc (buflen);
- if (*realname != NULL)
- {
- memcpy (*realname, buf, buflen);
- return fd;
- }
- else
- {
- /* No memory for the name, we certainly won't be able
- to load and link it. */
- __close (fd);
- return -1;
- }
- }
- if (here_any && (err = errno) != ENOENT && err != EACCES)
- /* The file exists and is readable, but something went wrong. */
- return -1;
-
- /* Remember whether we found anything. */
- any |= here_any;
- }
- while (*++dirs != NULL);
-
- /* Remove the whole path if none of the directories exists. */
- if (__glibc_unlikely (! any))
- {
- /* Paths which were allocated using the minimal malloc() in ld.so
- must not be freed using the general free() in libc. */
- if (sps->malloced)
- free (sps->dirs);
-
- /* rtld_search_dirs and env_path_list are attribute_relro, therefore
- avoid writing into it. */
- if (sps != &rtld_search_dirs && sps != &env_path_list)
- sps->dirs = (void *) -1;
- }
-
- return -1;
-}
-
-/* Map in the shared object file NAME. */
-
-struct link_map *
-internal_function
-_dl_map_object (struct link_map *loader, const char *name,
- int type, int trace_mode, int mode, Lmid_t nsid)
-{
- int fd;
- const char *origname = NULL;
- char *realname;
- char *name_copy;
- struct link_map *l;
- struct filebuf fb;
-
- assert (nsid >= 0);
- assert (nsid < GL(dl_nns));
-
- /* Look for this name among those already loaded. */
- for (l = GL(dl_ns)[nsid]._ns_loaded; l; l = l->l_next)
- {
- /* If the requested name matches the soname of a loaded object,
- use that object. Elide this check for names that have not
- yet been opened. */
- if (__glibc_unlikely ((l->l_faked | l->l_removed) != 0))
- continue;
- if (!_dl_name_match_p (name, l))
- {
- const char *soname;
-
- if (__glibc_likely (l->l_soname_added)
- || l->l_info[DT_SONAME] == NULL)
- continue;
-
- soname = ((const char *) D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[DT_SONAME]->d_un.d_val);
- if (strcmp (name, soname) != 0)
- continue;
-
- /* We have a match on a new name -- cache it. */
- add_name_to_object (l, soname);
- l->l_soname_added = 1;
- }
-
- /* We have a match. */
- return l;
- }
-
- /* Display information if we are debugging. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES)
- && loader != NULL)
- _dl_debug_printf ((mode & __RTLD_CALLMAP) == 0
- ? "\nfile=%s [%lu]; needed by %s [%lu]\n"
- : "\nfile=%s [%lu]; dynamically loaded by %s [%lu]\n",
- name, nsid, DSO_FILENAME (loader->l_name), loader->l_ns);
-
-#ifdef SHARED
- /* Give the auditing libraries a chance to change the name before we
- try anything. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0)
- && (loader == NULL || loader->l_auditing == 0))
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objsearch != NULL)
- {
- const char *before = name;
- name = afct->objsearch (name, &loader->l_audit[cnt].cookie,
- LA_SER_ORIG);
- if (name == NULL)
- {
- /* Do not try anything further. */
- fd = -1;
- goto no_file;
- }
- if (before != name && strcmp (before, name) != 0)
- {
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("audit changed filename %s -> %s\n",
- before, name);
-
- if (origname == NULL)
- origname = before;
- }
- }
-
- afct = afct->next;
- }
- }
-#endif
-
- /* Will be true if we found a DSO which is of the other ELF class. */
- bool found_other_class = false;
-
- if (strchr (name, '/') == NULL)
- {
- /* Search for NAME in several places. */
-
- size_t namelen = strlen (name) + 1;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS))
- _dl_debug_printf ("find library=%s [%lu]; searching\n", name, nsid);
-
- fd = -1;
-
- /* When the object has the RUNPATH information we don't use any
- RPATHs. */
- if (loader == NULL || loader->l_info[DT_RUNPATH] == NULL)
- {
- /* This is the executable's map (if there is one). Make sure that
- we do not look at it twice. */
- struct link_map *main_map = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
- bool did_main_map = false;
-
- /* First try the DT_RPATH of the dependent object that caused NAME
- to be loaded. Then that object's dependent, and on up. */
- for (l = loader; l; l = l->l_loader)
- if (cache_rpath (l, &l->l_rpath_dirs, DT_RPATH, "RPATH"))
- {
- fd = open_path (name, namelen, mode,
- &l->l_rpath_dirs,
- &realname, &fb, loader, LA_SER_RUNPATH,
- &found_other_class);
- if (fd != -1)
- break;
-
- did_main_map |= l == main_map;
- }
-
- /* If dynamically linked, try the DT_RPATH of the executable
- itself. NB: we do this for lookups in any namespace. */
- if (fd == -1 && !did_main_map
- && main_map != NULL && main_map->l_type != lt_loaded
- && cache_rpath (main_map, &main_map->l_rpath_dirs, DT_RPATH,
- "RPATH"))
- fd = open_path (name, namelen, mode,
- &main_map->l_rpath_dirs,
- &realname, &fb, loader ?: main_map, LA_SER_RUNPATH,
- &found_other_class);
- }
-
- /* Try the LD_LIBRARY_PATH environment variable. */
- if (fd == -1 && env_path_list.dirs != (void *) -1)
- fd = open_path (name, namelen, mode, &env_path_list,
- &realname, &fb,
- loader ?: GL(dl_ns)[LM_ID_BASE]._ns_loaded,
- LA_SER_LIBPATH, &found_other_class);
-
- /* Look at the RUNPATH information for this binary. */
- if (fd == -1 && loader != NULL
- && cache_rpath (loader, &loader->l_runpath_dirs,
- DT_RUNPATH, "RUNPATH"))
- fd = open_path (name, namelen, mode,
- &loader->l_runpath_dirs, &realname, &fb, loader,
- LA_SER_RUNPATH, &found_other_class);
-
- if (fd == -1)
- {
- realname = _dl_sysdep_open_object (name, namelen, &fd);
- if (realname != NULL)
- {
- fd = open_verify (realname, fd,
- &fb, loader ?: GL(dl_ns)[nsid]._ns_loaded,
- LA_SER_CONFIG, mode, &found_other_class,
- false);
- if (fd == -1)
- free (realname);
- }
- }
-
-#ifdef USE_LDCONFIG
- if (fd == -1
- && (__glibc_likely ((mode & __RTLD_SECURE) == 0)
- || ! __libc_enable_secure)
- && __glibc_likely (GLRO(dl_inhibit_cache) == 0))
- {
- /* Check the list of libraries in the file /etc/ld.so.cache,
- for compatibility with Linux's ldconfig program. */
- char *cached = _dl_load_cache_lookup (name);
-
- if (cached != NULL)
- {
- // XXX Correct to unconditionally default to namespace 0?
- l = (loader
- ?: GL(dl_ns)[LM_ID_BASE]._ns_loaded
-# ifdef SHARED
- ?: &GL(dl_rtld_map)
-# endif
- );
-
- /* If the loader has the DF_1_NODEFLIB flag set we must not
- use a cache entry from any of these directories. */
- if (__glibc_unlikely (l->l_flags_1 & DF_1_NODEFLIB))
- {
- const char *dirp = system_dirs;
- unsigned int cnt = 0;
-
- do
- {
- if (memcmp (cached, dirp, system_dirs_len[cnt]) == 0)
- {
- /* The prefix matches. Don't use the entry. */
- free (cached);
- cached = NULL;
- break;
- }
-
- dirp += system_dirs_len[cnt] + 1;
- ++cnt;
- }
- while (cnt < nsystem_dirs_len);
- }
-
- if (cached != NULL)
- {
- fd = open_verify (cached, -1,
- &fb, loader ?: GL(dl_ns)[nsid]._ns_loaded,
- LA_SER_CONFIG, mode, &found_other_class,
- false);
- if (__glibc_likely (fd != -1))
- realname = cached;
- else
- free (cached);
- }
- }
- }
-#endif
-
- /* Finally, try the default path. */
- if (fd == -1
- && ((l = loader ?: GL(dl_ns)[nsid]._ns_loaded) == NULL
- || __glibc_likely (!(l->l_flags_1 & DF_1_NODEFLIB)))
- && rtld_search_dirs.dirs != (void *) -1)
- fd = open_path (name, namelen, mode, &rtld_search_dirs,
- &realname, &fb, l, LA_SER_DEFAULT, &found_other_class);
-
- /* Add another newline when we are tracing the library loading. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS))
- _dl_debug_printf ("\n");
- }
- else
- {
- /* The path may contain dynamic string tokens. */
- realname = (loader
- ? expand_dynamic_string_token (loader, name, 0)
- : __strdup (name));
- if (realname == NULL)
- fd = -1;
- else
- {
- fd = open_verify (realname, -1, &fb,
- loader ?: GL(dl_ns)[nsid]._ns_loaded, 0, mode,
- &found_other_class, true);
- if (__glibc_unlikely (fd == -1))
- free (realname);
- }
- }
-
-#ifdef SHARED
- no_file:
-#endif
- /* In case the LOADER information has only been provided to get to
- the appropriate RUNPATH/RPATH information we do not need it
- anymore. */
- if (mode & __RTLD_CALLMAP)
- loader = NULL;
-
- if (__glibc_unlikely (fd == -1))
- {
- if (trace_mode
- && __glibc_likely ((GLRO(dl_debug_mask) & DL_DEBUG_PRELINK) == 0))
- {
- /* We haven't found an appropriate library. But since we
- are only interested in the list of libraries this isn't
- so severe. Fake an entry with all the information we
- have. */
- static const Elf_Symndx dummy_bucket = STN_UNDEF;
-
- /* Allocate a new object map. */
- if ((name_copy = __strdup (name)) == NULL
- || (l = _dl_new_object (name_copy, name, type, loader,
- mode, nsid)) == NULL)
- {
- free (name_copy);
- _dl_signal_error (ENOMEM, name, NULL,
- N_("cannot create shared object descriptor"));
- }
- /* Signal that this is a faked entry. */
- l->l_faked = 1;
- /* Since the descriptor is initialized with zero we do not
- have do this here.
- l->l_reserved = 0; */
- l->l_buckets = &dummy_bucket;
- l->l_nbuckets = 1;
- l->l_relocated = 1;
-
- /* Enter the object in the object list. */
- _dl_add_to_namespace_list (l, nsid);
-
- return l;
- }
- else if (found_other_class)
- _dl_signal_error (0, name, NULL,
- ELFW(CLASS) == ELFCLASS32
- ? N_("wrong ELF class: ELFCLASS64")
- : N_("wrong ELF class: ELFCLASS32"));
- else
- _dl_signal_error (errno, name, NULL,
- N_("cannot open shared object file"));
- }
-
- void *stack_end = __libc_stack_end;
- return _dl_map_object_from_fd (name, origname, fd, &fb, realname, loader,
- type, mode, &stack_end, nsid);
-}
-
-struct add_path_state
-{
- bool counting;
- unsigned int idx;
- Dl_serinfo *si;
- char *allocptr;
-};
-
-static void
-add_path (struct add_path_state *p, const struct r_search_path_struct *sps,
- unsigned int flags)
-{
- if (sps->dirs != (void *) -1)
- {
- struct r_search_path_elem **dirs = sps->dirs;
- do
- {
- const struct r_search_path_elem *const r = *dirs++;
- if (p->counting)
- {
- p->si->dls_cnt++;
- p->si->dls_size += MAX (2, r->dirnamelen);
- }
- else
- {
- Dl_serpath *const sp = &p->si->dls_serpath[p->idx++];
- sp->dls_name = p->allocptr;
- if (r->dirnamelen < 2)
- *p->allocptr++ = r->dirnamelen ? '/' : '.';
- else
- p->allocptr = __mempcpy (p->allocptr,
- r->dirname, r->dirnamelen - 1);
- *p->allocptr++ = '\0';
- sp->dls_flags = flags;
- }
- }
- while (*dirs != NULL);
- }
-}
-
-void
-internal_function
-_dl_rtld_di_serinfo (struct link_map *loader, Dl_serinfo *si, bool counting)
-{
- if (counting)
- {
- si->dls_cnt = 0;
- si->dls_size = 0;
- }
-
- struct add_path_state p =
- {
- .counting = counting,
- .idx = 0,
- .si = si,
- .allocptr = (char *) &si->dls_serpath[si->dls_cnt]
- };
-
-# define add_path(p, sps, flags) add_path(p, sps, 0) /* XXX */
-
- /* When the object has the RUNPATH information we don't use any RPATHs. */
- if (loader->l_info[DT_RUNPATH] == NULL)
- {
- /* First try the DT_RPATH of the dependent object that caused NAME
- to be loaded. Then that object's dependent, and on up. */
-
- struct link_map *l = loader;
- do
- {
- if (cache_rpath (l, &l->l_rpath_dirs, DT_RPATH, "RPATH"))
- add_path (&p, &l->l_rpath_dirs, XXX_RPATH);
- l = l->l_loader;
- }
- while (l != NULL);
-
- /* If dynamically linked, try the DT_RPATH of the executable itself. */
- if (loader->l_ns == LM_ID_BASE)
- {
- l = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
- if (l != NULL && l->l_type != lt_loaded && l != loader)
- if (cache_rpath (l, &l->l_rpath_dirs, DT_RPATH, "RPATH"))
- add_path (&p, &l->l_rpath_dirs, XXX_RPATH);
- }
- }
-
- /* Try the LD_LIBRARY_PATH environment variable. */
- add_path (&p, &env_path_list, XXX_ENV);
-
- /* Look at the RUNPATH information for this binary. */
- if (cache_rpath (loader, &loader->l_runpath_dirs, DT_RUNPATH, "RUNPATH"))
- add_path (&p, &loader->l_runpath_dirs, XXX_RUNPATH);
-
- /* XXX
- Here is where ld.so.cache gets checked, but we don't have
- a way to indicate that in the results for Dl_serinfo. */
-
- /* Finally, try the default path. */
- if (!(loader->l_flags_1 & DF_1_NODEFLIB))
- add_path (&p, &rtld_search_dirs, XXX_default);
-
- if (counting)
- /* Count the struct size before the string area, which we didn't
- know before we completed dls_cnt. */
- si->dls_size += (char *) &si->dls_serpath[si->dls_cnt] - (char *) si;
-}
diff --git a/elf/dl-load.h b/elf/dl-load.h
deleted file mode 100644
index 7cd6214d4e..0000000000
--- a/elf/dl-load.h
+++ /dev/null
@@ -1,135 +0,0 @@
-/* Map in a shared object's segments from the file.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _DL_LOAD_H
-#define _DL_LOAD_H 1
-
-#include <link.h>
-#include <sys/mman.h>
-
-
-/* On some systems, no flag bits are given to specify file mapping. */
-#ifndef MAP_FILE
-# define MAP_FILE 0
-#endif
-
-/* The right way to map in the shared library files is MAP_COPY, which
- makes a virtual copy of the data at the time of the mmap call; this
- guarantees the mapped pages will be consistent even if the file is
- overwritten. Some losing VM systems like Linux's lack MAP_COPY. All we
- get is MAP_PRIVATE, which copies each page when it is modified; this
- means if the file is overwritten, we may at some point get some pages
- from the new version after starting with pages from the old version.
-
- To make up for the lack and avoid the overwriting problem,
- what Linux does have is MAP_DENYWRITE. This prevents anyone
- from modifying the file while we have it mapped. */
-#ifndef MAP_COPY
-# ifdef MAP_DENYWRITE
-# define MAP_COPY (MAP_PRIVATE | MAP_DENYWRITE)
-# else
-# define MAP_COPY MAP_PRIVATE
-# endif
-#endif
-
-/* Some systems link their relocatable objects for another base address
- than 0. We want to know the base address for these such that we can
- subtract this address from the segment addresses during mapping.
- This results in a more efficient address space usage. Defaults to
- zero for almost all systems. */
-#ifndef MAP_BASE_ADDR
-# define MAP_BASE_ADDR(l) 0
-#endif
-
-
-/* Handle situations where we have a preferred location in memory for
- the shared objects. */
-#ifdef ELF_PREFERRED_ADDRESS_DATA
-ELF_PREFERRED_ADDRESS_DATA;
-#endif
-#ifndef ELF_PREFERRED_ADDRESS
-# define ELF_PREFERRED_ADDRESS(loader, maplength, mapstartpref) (mapstartpref)
-#endif
-#ifndef ELF_FIXED_ADDRESS
-# define ELF_FIXED_ADDRESS(loader, mapstart) ((void) 0)
-#endif
-
-
-/* This structure describes one PT_LOAD command.
- Its details have been expanded out and converted. */
-struct loadcmd
-{
- ElfW(Addr) mapstart, mapend, dataend, allocend;
- ElfW(Off) mapoff;
- int prot; /* PROT_* bits. */
-};
-
-
-/* This is a subroutine of _dl_map_segments. It should be called for each
- load command, some time after L->l_addr has been set correctly. It is
- responsible for setting up the l_text_end and l_phdr fields. */
-static void __always_inline
-_dl_postprocess_loadcmd (struct link_map *l, const ElfW(Ehdr) *header,
- const struct loadcmd *c)
-{
- if (c->prot & PROT_EXEC)
- l->l_text_end = l->l_addr + c->mapend;
-
- if (l->l_phdr == 0
- && c->mapoff <= header->e_phoff
- && ((size_t) (c->mapend - c->mapstart + c->mapoff)
- >= header->e_phoff + header->e_phnum * sizeof (ElfW(Phdr))))
- /* Found the program header in this segment. */
- l->l_phdr = (void *) (uintptr_t) (c->mapstart + header->e_phoff
- - c->mapoff);
-}
-
-
-/* This is a subroutine of _dl_map_object_from_fd. It is responsible
- for filling in several fields in *L: l_map_start, l_map_end, l_addr,
- l_contiguous, l_text_end, l_phdr. On successful return, all the
- segments are mapped (or copied, or whatever) from the file into their
- final places in the address space, with the correct page permissions,
- and any bss-like regions already zeroed. It returns a null pointer
- on success, or an error message string (to be translated) on error
- (having also set errno).
-
- The file <dl-map-segments.h> defines this function. The canonical
- implementation in elf/dl-map-segments.h might be replaced by a sysdeps
- version. */
-static const char *_dl_map_segments (struct link_map *l, int fd,
- const ElfW(Ehdr) *header, int type,
- const struct loadcmd loadcmds[],
- size_t nloadcmds,
- const size_t maplength,
- bool has_holes,
- struct link_map *loader);
-
-/* All the error message strings _dl_map_segments might return are
- listed here so that different implementations in different sysdeps
- dl-map-segments.h files all use consistent strings that are
- guaranteed to have translations. */
-#define DL_MAP_SEGMENTS_ERROR_MAP_SEGMENT \
- N_("failed to map segment from shared object")
-#define DL_MAP_SEGMENTS_ERROR_MPROTECT \
- N_("cannot change memory protections")
-#define DL_MAP_SEGMENTS_ERROR_MAP_ZERO_FILL \
- N_("cannot map zero-fill pages")
-
-
-#endif /* dl-load.h */
diff --git a/elf/dl-lookup.c b/elf/dl-lookup.c
deleted file mode 100644
index 3d2369dbf2..0000000000
--- a/elf/dl-lookup.c
+++ /dev/null
@@ -1,1129 +0,0 @@
-/* Look up a symbol in the loaded objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <alloca.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <dl-hash.h>
-#include <dl-machine.h>
-#include <sysdep-cancel.h>
-#include <libc-lock.h>
-#include <tls.h>
-#include <atomic.h>
-
-#include <assert.h>
-
-/* Return nonzero if check_match should consider SYM to fail to match a
- symbol reference for some machine-specific reason. */
-#ifndef ELF_MACHINE_SYM_NO_MATCH
-# define ELF_MACHINE_SYM_NO_MATCH(sym) 0
-#endif
-
-#define VERSTAG(tag) (DT_NUM + DT_THISPROCNUM + DT_VERSIONTAGIDX (tag))
-
-
-struct sym_val
- {
- const ElfW(Sym) *s;
- struct link_map *m;
- };
-
-
-#define make_string(string, rest...) \
- ({ \
- const char *all[] = { string, ## rest }; \
- size_t len, cnt; \
- char *result, *cp; \
- \
- len = 1; \
- for (cnt = 0; cnt < sizeof (all) / sizeof (all[0]); ++cnt) \
- len += strlen (all[cnt]); \
- \
- cp = result = alloca (len); \
- for (cnt = 0; cnt < sizeof (all) / sizeof (all[0]); ++cnt) \
- cp = __stpcpy (cp, all[cnt]); \
- \
- result; \
- })
-
-/* Statistics function. */
-#ifdef SHARED
-# define bump_num_relocations() ++GL(dl_num_relocations)
-#else
-# define bump_num_relocations() ((void) 0)
-#endif
-
-/* Utility function for do_lookup_x. The caller is called with undef_name,
- ref, version, flags and type_class, and those are passed as the first
- five arguments. The caller then computes sym, symidx, strtab, and map
- and passes them as the next four arguments. Lastly the caller passes in
- versioned_sym and num_versions which are modified by check_match during
- the checking process. */
-static const ElfW(Sym) *
-check_match (const char *const undef_name,
- const ElfW(Sym) *const ref,
- const struct r_found_version *const version,
- const int flags,
- const int type_class,
- const ElfW(Sym) *const sym,
- const Elf_Symndx symidx,
- const char *const strtab,
- const struct link_map *const map,
- const ElfW(Sym) **const versioned_sym,
- int *const num_versions)
-{
- unsigned int stt = ELFW(ST_TYPE) (sym->st_info);
- assert (ELF_RTYPE_CLASS_PLT == 1);
- if (__glibc_unlikely ((sym->st_value == 0 /* No value. */
- && stt != STT_TLS)
- || ELF_MACHINE_SYM_NO_MATCH (sym)
- || (type_class & (sym->st_shndx == SHN_UNDEF))))
- return NULL;
-
- /* Ignore all but STT_NOTYPE, STT_OBJECT, STT_FUNC,
- STT_COMMON, STT_TLS, and STT_GNU_IFUNC since these are no
- code/data definitions. */
-#define ALLOWED_STT \
- ((1 << STT_NOTYPE) | (1 << STT_OBJECT) | (1 << STT_FUNC) \
- | (1 << STT_COMMON) | (1 << STT_TLS) | (1 << STT_GNU_IFUNC))
- if (__glibc_unlikely (((1 << stt) & ALLOWED_STT) == 0))
- return NULL;
-
- if (sym != ref && strcmp (strtab + sym->st_name, undef_name))
- /* Not the symbol we are looking for. */
- return NULL;
-
- const ElfW(Half) *verstab = map->l_versyms;
- if (version != NULL)
- {
- if (__glibc_unlikely (verstab == NULL))
- {
- /* We need a versioned symbol but haven't found any. If
- this is the object which is referenced in the verneed
- entry it is a bug in the library since a symbol must
- not simply disappear.
-
- It would also be a bug in the object since it means that
- the list of required versions is incomplete and so the
- tests in dl-version.c haven't found a problem.*/
- assert (version->filename == NULL
- || ! _dl_name_match_p (version->filename, map));
-
- /* Otherwise we accept the symbol. */
- }
- else
- {
- /* We can match the version information or use the
- default one if it is not hidden. */
- ElfW(Half) ndx = verstab[symidx] & 0x7fff;
- if ((map->l_versions[ndx].hash != version->hash
- || strcmp (map->l_versions[ndx].name, version->name))
- && (version->hidden || map->l_versions[ndx].hash
- || (verstab[symidx] & 0x8000)))
- /* It's not the version we want. */
- return NULL;
- }
- }
- else
- {
- /* No specific version is selected. There are two ways we
- can got here:
-
- - a binary which does not include versioning information
- is loaded
-
- - dlsym() instead of dlvsym() is used to get a symbol which
- might exist in more than one form
-
- If the library does not provide symbol version information
- there is no problem at all: we simply use the symbol if it
- is defined.
-
- These two lookups need to be handled differently if the
- library defines versions. In the case of the old
- unversioned application the oldest (default) version
- should be used. In case of a dlsym() call the latest and
- public interface should be returned. */
- if (verstab != NULL)
- {
- if ((verstab[symidx] & 0x7fff)
- >= ((flags & DL_LOOKUP_RETURN_NEWEST) ? 2 : 3))
- {
- /* Don't accept hidden symbols. */
- if ((verstab[symidx] & 0x8000) == 0
- && (*num_versions)++ == 0)
- /* No version so far. */
- *versioned_sym = sym;
-
- return NULL;
- }
- }
- }
-
- /* There cannot be another entry for this symbol so stop here. */
- return sym;
-}
-
-/* Utility function for do_lookup_unique. Add a symbol to TABLE. */
-static void
-enter_unique_sym (struct unique_sym *table, size_t size,
- unsigned int hash, const char *name,
- const ElfW(Sym) *sym, const struct link_map *map)
-{
- size_t idx = hash % size;
- size_t hash2 = 1 + hash % (size - 2);
- while (table[idx].name != NULL)
- {
- idx += hash2;
- if (idx >= size)
- idx -= size;
- }
-
- table[idx].hashval = hash;
- table[idx].name = name;
- table[idx].sym = sym;
- table[idx].map = map;
-}
-
-/* Utility function for do_lookup_x. Lookup an STB_GNU_UNIQUE symbol
- in the unique symbol table, creating a new entry if necessary.
- Return the matching symbol in RESULT. */
-static void
-do_lookup_unique (const char *undef_name, uint_fast32_t new_hash,
- const struct link_map *map, struct sym_val *result,
- int type_class, const ElfW(Sym) *sym, const char *strtab,
- const ElfW(Sym) *ref, const struct link_map *undef_map)
-{
- /* We have to determine whether we already found a symbol with this
- name before. If not then we have to add it to the search table.
- If we already found a definition we have to use it. */
-
- struct unique_sym_table *tab
- = &GL(dl_ns)[map->l_ns]._ns_unique_sym_table;
-
- __rtld_lock_lock_recursive (tab->lock);
-
- struct unique_sym *entries = tab->entries;
- size_t size = tab->size;
- if (entries != NULL)
- {
- size_t idx = new_hash % size;
- size_t hash2 = 1 + new_hash % (size - 2);
- while (1)
- {
- if (entries[idx].hashval == new_hash
- && strcmp (entries[idx].name, undef_name) == 0)
- {
- if ((type_class & ELF_RTYPE_CLASS_COPY) != 0)
- {
- /* We possibly have to initialize the central
- copy from the copy addressed through the
- relocation. */
- result->s = sym;
- result->m = (struct link_map *) map;
- }
- else
- {
- result->s = entries[idx].sym;
- result->m = (struct link_map *) entries[idx].map;
- }
- __rtld_lock_unlock_recursive (tab->lock);
- return;
- }
-
- if (entries[idx].name == NULL)
- break;
-
- idx += hash2;
- if (idx >= size)
- idx -= size;
- }
-
- if (size * 3 <= tab->n_elements * 4)
- {
- /* Expand the table. */
-#ifdef RTLD_CHECK_FOREIGN_CALL
- /* This must not happen during runtime relocations. */
- assert (!RTLD_CHECK_FOREIGN_CALL);
-#endif
- size_t newsize = _dl_higher_prime_number (size + 1);
- struct unique_sym *newentries
- = calloc (sizeof (struct unique_sym), newsize);
- if (newentries == NULL)
- {
- nomem:
- __rtld_lock_unlock_recursive (tab->lock);
- _dl_fatal_printf ("out of memory\n");
- }
-
- for (idx = 0; idx < size; ++idx)
- if (entries[idx].name != NULL)
- enter_unique_sym (newentries, newsize, entries[idx].hashval,
- entries[idx].name, entries[idx].sym,
- entries[idx].map);
-
- tab->free (entries);
- tab->size = newsize;
- size = newsize;
- entries = tab->entries = newentries;
- tab->free = free;
- }
- }
- else
- {
-#ifdef RTLD_CHECK_FOREIGN_CALL
- /* This must not happen during runtime relocations. */
- assert (!RTLD_CHECK_FOREIGN_CALL);
-#endif
-
-#ifdef SHARED
- /* If tab->entries is NULL, but tab->size is not, it means
- this is the second, conflict finding, lookup for
- LD_TRACE_PRELINKING in _dl_debug_bindings. Don't
- allocate anything and don't enter anything into the
- hash table. */
- if (__glibc_unlikely (tab->size))
- {
- assert (GLRO(dl_debug_mask) & DL_DEBUG_PRELINK);
- goto success;
- }
-#endif
-
-#define INITIAL_NUNIQUE_SYM_TABLE 31
- size = INITIAL_NUNIQUE_SYM_TABLE;
- entries = calloc (sizeof (struct unique_sym), size);
- if (entries == NULL)
- goto nomem;
-
- tab->entries = entries;
- tab->size = size;
- tab->free = free;
- }
-
- if ((type_class & ELF_RTYPE_CLASS_COPY) != 0)
- enter_unique_sym (entries, size, new_hash, strtab + sym->st_name, ref,
- undef_map);
- else
- {
- enter_unique_sym (entries, size,
- new_hash, strtab + sym->st_name, sym, map);
-
- if (map->l_type == lt_loaded)
- /* Make sure we don't unload this object by
- setting the appropriate flag. */
- ((struct link_map *) map)->l_flags_1 |= DF_1_NODELETE;
- }
- ++tab->n_elements;
-
-#ifdef SHARED
- success:
-#endif
- __rtld_lock_unlock_recursive (tab->lock);
-
- result->s = sym;
- result->m = (struct link_map *) map;
-}
-
-/* Inner part of the lookup functions. We return a value > 0 if we
- found the symbol, the value 0 if nothing is found and < 0 if
- something bad happened. */
-static int
-__attribute_noinline__
-do_lookup_x (const char *undef_name, uint_fast32_t new_hash,
- unsigned long int *old_hash, const ElfW(Sym) *ref,
- struct sym_val *result, struct r_scope_elem *scope, size_t i,
- const struct r_found_version *const version, int flags,
- struct link_map *skip, int type_class, struct link_map *undef_map)
-{
- size_t n = scope->r_nlist;
- /* Make sure we read the value before proceeding. Otherwise we
- might use r_list pointing to the initial scope and r_nlist being
- the value after a resize. That is the only path in dl-open.c not
- protected by GSCOPE. A read barrier here might be to expensive. */
- __asm volatile ("" : "+r" (n), "+m" (scope->r_list));
- struct link_map **list = scope->r_list;
-
- do
- {
- const struct link_map *map = list[i]->l_real;
-
- /* Here come the extra test needed for `_dl_lookup_symbol_skip'. */
- if (map == skip)
- continue;
-
- /* Don't search the executable when resolving a copy reloc. */
- if ((type_class & ELF_RTYPE_CLASS_COPY) && map->l_type == lt_executable)
- continue;
-
- /* Do not look into objects which are going to be removed. */
- if (map->l_removed)
- continue;
-
- /* Print some debugging info if wanted. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_SYMBOLS))
- _dl_debug_printf ("symbol=%s; lookup in file=%s [%lu]\n",
- undef_name, DSO_FILENAME (map->l_name),
- map->l_ns);
-
- /* If the hash table is empty there is nothing to do here. */
- if (map->l_nbuckets == 0)
- continue;
-
- Elf_Symndx symidx;
- int num_versions = 0;
- const ElfW(Sym) *versioned_sym = NULL;
-
- /* The tables for this map. */
- const ElfW(Sym) *symtab = (const void *) D_PTR (map, l_info[DT_SYMTAB]);
- const char *strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
-
- const ElfW(Sym) *sym;
- const ElfW(Addr) *bitmask = map->l_gnu_bitmask;
- if (__glibc_likely (bitmask != NULL))
- {
- ElfW(Addr) bitmask_word
- = bitmask[(new_hash / __ELF_NATIVE_CLASS)
- & map->l_gnu_bitmask_idxbits];
-
- unsigned int hashbit1 = new_hash & (__ELF_NATIVE_CLASS - 1);
- unsigned int hashbit2 = ((new_hash >> map->l_gnu_shift)
- & (__ELF_NATIVE_CLASS - 1));
-
- if (__glibc_unlikely ((bitmask_word >> hashbit1)
- & (bitmask_word >> hashbit2) & 1))
- {
- Elf32_Word bucket = map->l_gnu_buckets[new_hash
- % map->l_nbuckets];
- if (bucket != 0)
- {
- const Elf32_Word *hasharr = &map->l_gnu_chain_zero[bucket];
-
- do
- if (((*hasharr ^ new_hash) >> 1) == 0)
- {
- symidx = hasharr - map->l_gnu_chain_zero;
- sym = check_match (undef_name, ref, version, flags,
- type_class, &symtab[symidx], symidx,
- strtab, map, &versioned_sym,
- &num_versions);
- if (sym != NULL)
- goto found_it;
- }
- while ((*hasharr++ & 1u) == 0);
- }
- }
- /* No symbol found. */
- symidx = SHN_UNDEF;
- }
- else
- {
- if (*old_hash == 0xffffffff)
- *old_hash = _dl_elf_hash (undef_name);
-
- /* Use the old SysV-style hash table. Search the appropriate
- hash bucket in this object's symbol table for a definition
- for the same symbol name. */
- for (symidx = map->l_buckets[*old_hash % map->l_nbuckets];
- symidx != STN_UNDEF;
- symidx = map->l_chain[symidx])
- {
- sym = check_match (undef_name, ref, version, flags,
- type_class, &symtab[symidx], symidx,
- strtab, map, &versioned_sym,
- &num_versions);
- if (sym != NULL)
- goto found_it;
- }
- }
-
- /* If we have seen exactly one versioned symbol while we are
- looking for an unversioned symbol and the version is not the
- default version we still accept this symbol since there are
- no possible ambiguities. */
- sym = num_versions == 1 ? versioned_sym : NULL;
-
- if (sym != NULL)
- {
- found_it:
- /* When UNDEF_MAP is NULL, which indicates we are called from
- do_lookup_x on relocation against protected data, we skip
- the data definion in the executable from copy reloc. */
- if (ELF_RTYPE_CLASS_EXTERN_PROTECTED_DATA
- && undef_map == NULL
- && map->l_type == lt_executable
- && type_class == ELF_RTYPE_CLASS_EXTERN_PROTECTED_DATA)
- {
- const ElfW(Sym) *s;
- unsigned int i;
-
-#if ! ELF_MACHINE_NO_RELA
- if (map->l_info[DT_RELA] != NULL
- && map->l_info[DT_RELASZ] != NULL
- && map->l_info[DT_RELASZ]->d_un.d_val != 0)
- {
- const ElfW(Rela) *rela
- = (const ElfW(Rela) *) D_PTR (map, l_info[DT_RELA]);
- unsigned int rela_count
- = map->l_info[DT_RELASZ]->d_un.d_val / sizeof (*rela);
-
- for (i = 0; i < rela_count; i++, rela++)
- if (elf_machine_type_class (ELFW(R_TYPE) (rela->r_info))
- == ELF_RTYPE_CLASS_COPY)
- {
- s = &symtab[ELFW(R_SYM) (rela->r_info)];
- if (!strcmp (strtab + s->st_name, undef_name))
- goto skip;
- }
- }
-#endif
-#if ! ELF_MACHINE_NO_REL
- if (map->l_info[DT_REL] != NULL
- && map->l_info[DT_RELSZ] != NULL
- && map->l_info[DT_RELSZ]->d_un.d_val != 0)
- {
- const ElfW(Rel) *rel
- = (const ElfW(Rel) *) D_PTR (map, l_info[DT_REL]);
- unsigned int rel_count
- = map->l_info[DT_RELSZ]->d_un.d_val / sizeof (*rel);
-
- for (i = 0; i < rel_count; i++, rel++)
- if (elf_machine_type_class (ELFW(R_TYPE) (rel->r_info))
- == ELF_RTYPE_CLASS_COPY)
- {
- s = &symtab[ELFW(R_SYM) (rel->r_info)];
- if (!strcmp (strtab + s->st_name, undef_name))
- goto skip;
- }
- }
-#endif
- }
-
- /* Hidden and internal symbols are local, ignore them. */
- if (__glibc_unlikely (dl_symbol_visibility_binds_local_p (sym)))
- goto skip;
-
- switch (ELFW(ST_BIND) (sym->st_info))
- {
- case STB_WEAK:
- /* Weak definition. Use this value if we don't find another. */
- if (__glibc_unlikely (GLRO(dl_dynamic_weak)))
- {
- if (! result->s)
- {
- result->s = sym;
- result->m = (struct link_map *) map;
- }
- break;
- }
- /* FALLTHROUGH */
- case STB_GLOBAL:
- /* Global definition. Just what we need. */
- result->s = sym;
- result->m = (struct link_map *) map;
- return 1;
-
- case STB_GNU_UNIQUE:;
- do_lookup_unique (undef_name, new_hash, map, result, type_class,
- sym, strtab, ref, undef_map);
- return 1;
-
- default:
- /* Local symbols are ignored. */
- break;
- }
- }
-
-skip:
- /* If this current map is the one mentioned in the verneed entry
- and we have not found a weak entry, it is a bug. */
- if (symidx == STN_UNDEF && version != NULL && version->filename != NULL
- && __glibc_unlikely (_dl_name_match_p (version->filename, map)))
- return -1;
- }
- while (++i < n);
-
- /* We have not found anything until now. */
- return 0;
-}
-
-
-static uint_fast32_t
-dl_new_hash (const char *s)
-{
- uint_fast32_t h = 5381;
- for (unsigned char c = *s; c != '\0'; c = *++s)
- h = h * 33 + c;
- return h & 0xffffffff;
-}
-
-
-/* Add extra dependency on MAP to UNDEF_MAP. */
-static int
-internal_function
-add_dependency (struct link_map *undef_map, struct link_map *map, int flags)
-{
- struct link_map *runp;
- unsigned int i;
- int result = 0;
-
- /* Avoid self-references and references to objects which cannot be
- unloaded anyway. */
- if (undef_map == map)
- return 0;
-
- /* Avoid references to objects which cannot be unloaded anyway. */
- assert (map->l_type == lt_loaded);
- if ((map->l_flags_1 & DF_1_NODELETE) != 0)
- return 0;
-
- struct link_map_reldeps *l_reldeps
- = atomic_forced_read (undef_map->l_reldeps);
-
- /* Make sure l_reldeps is read before l_initfini. */
- atomic_read_barrier ();
-
- /* Determine whether UNDEF_MAP already has a reference to MAP. First
- look in the normal dependencies. */
- struct link_map **l_initfini = atomic_forced_read (undef_map->l_initfini);
- if (l_initfini != NULL)
- {
- for (i = 0; l_initfini[i] != NULL; ++i)
- if (l_initfini[i] == map)
- return 0;
- }
-
- /* No normal dependency. See whether we already had to add it
- to the special list of dynamic dependencies. */
- unsigned int l_reldepsact = 0;
- if (l_reldeps != NULL)
- {
- struct link_map **list = &l_reldeps->list[0];
- l_reldepsact = l_reldeps->act;
- for (i = 0; i < l_reldepsact; ++i)
- if (list[i] == map)
- return 0;
- }
-
- /* Save serial number of the target MAP. */
- unsigned long long serial = map->l_serial;
-
- /* Make sure nobody can unload the object while we are at it. */
- if (__glibc_unlikely (flags & DL_LOOKUP_GSCOPE_LOCK))
- {
- /* We can't just call __rtld_lock_lock_recursive (GL(dl_load_lock))
- here, that can result in ABBA deadlock. */
- THREAD_GSCOPE_RESET_FLAG ();
- __rtld_lock_lock_recursive (GL(dl_load_lock));
- /* While MAP value won't change, after THREAD_GSCOPE_RESET_FLAG ()
- it can e.g. point to unallocated memory. So avoid the optimizer
- treating the above read from MAP->l_serial as ensurance it
- can safely dereference it. */
- map = atomic_forced_read (map);
-
- /* From this point on it is unsafe to dereference MAP, until it
- has been found in one of the lists. */
-
- /* Redo the l_initfini check in case undef_map's l_initfini
- changed in the mean time. */
- if (undef_map->l_initfini != l_initfini
- && undef_map->l_initfini != NULL)
- {
- l_initfini = undef_map->l_initfini;
- for (i = 0; l_initfini[i] != NULL; ++i)
- if (l_initfini[i] == map)
- goto out_check;
- }
-
- /* Redo the l_reldeps check if undef_map's l_reldeps changed in
- the mean time. */
- if (undef_map->l_reldeps != NULL)
- {
- if (undef_map->l_reldeps != l_reldeps)
- {
- struct link_map **list = &undef_map->l_reldeps->list[0];
- l_reldepsact = undef_map->l_reldeps->act;
- for (i = 0; i < l_reldepsact; ++i)
- if (list[i] == map)
- goto out_check;
- }
- else if (undef_map->l_reldeps->act > l_reldepsact)
- {
- struct link_map **list
- = &undef_map->l_reldeps->list[0];
- i = l_reldepsact;
- l_reldepsact = undef_map->l_reldeps->act;
- for (; i < l_reldepsact; ++i)
- if (list[i] == map)
- goto out_check;
- }
- }
- }
- else
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- /* The object is not yet in the dependency list. Before we add
- it make sure just one more time the object we are about to
- reference is still available. There is a brief period in
- which the object could have been removed since we found the
- definition. */
- runp = GL(dl_ns)[undef_map->l_ns]._ns_loaded;
- while (runp != NULL && runp != map)
- runp = runp->l_next;
-
- if (runp != NULL)
- {
- /* The object is still available. */
-
- /* MAP could have been dlclosed, freed and then some other dlopened
- library could have the same link_map pointer. */
- if (map->l_serial != serial)
- goto out_check;
-
- /* Redo the NODELETE check, as when dl_load_lock wasn't held
- yet this could have changed. */
- if ((map->l_flags_1 & DF_1_NODELETE) != 0)
- goto out;
-
- /* If the object with the undefined reference cannot be removed ever
- just make sure the same is true for the object which contains the
- definition. */
- if (undef_map->l_type != lt_loaded
- || (undef_map->l_flags_1 & DF_1_NODELETE) != 0)
- {
- map->l_flags_1 |= DF_1_NODELETE;
- goto out;
- }
-
- /* Add the reference now. */
- if (__glibc_unlikely (l_reldepsact >= undef_map->l_reldepsmax))
- {
- /* Allocate more memory for the dependency list. Since this
- can never happen during the startup phase we can use
- `realloc'. */
- struct link_map_reldeps *newp;
- unsigned int max
- = undef_map->l_reldepsmax ? undef_map->l_reldepsmax * 2 : 10;
-
-#ifdef RTLD_PREPARE_FOREIGN_CALL
- RTLD_PREPARE_FOREIGN_CALL;
-#endif
-
- newp = malloc (sizeof (*newp) + max * sizeof (struct link_map *));
- if (newp == NULL)
- {
- /* If we didn't manage to allocate memory for the list this is
- no fatal problem. We simply make sure the referenced object
- cannot be unloaded. This is semantically the correct
- behavior. */
- map->l_flags_1 |= DF_1_NODELETE;
- goto out;
- }
- else
- {
- if (l_reldepsact)
- memcpy (&newp->list[0], &undef_map->l_reldeps->list[0],
- l_reldepsact * sizeof (struct link_map *));
- newp->list[l_reldepsact] = map;
- newp->act = l_reldepsact + 1;
- atomic_write_barrier ();
- void *old = undef_map->l_reldeps;
- undef_map->l_reldeps = newp;
- undef_map->l_reldepsmax = max;
- if (old)
- _dl_scope_free (old);
- }
- }
- else
- {
- undef_map->l_reldeps->list[l_reldepsact] = map;
- atomic_write_barrier ();
- undef_map->l_reldeps->act = l_reldepsact + 1;
- }
-
- /* Display information if we are debugging. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("\
-\nfile=%s [%lu]; needed by %s [%lu] (relocation dependency)\n\n",
- DSO_FILENAME (map->l_name),
- map->l_ns,
- DSO_FILENAME (undef_map->l_name),
- undef_map->l_ns);
- }
- else
- /* Whoa, that was bad luck. We have to search again. */
- result = -1;
-
- out:
- /* Release the lock. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- if (__glibc_unlikely (flags & DL_LOOKUP_GSCOPE_LOCK))
- THREAD_GSCOPE_SET_FLAG ();
-
- return result;
-
- out_check:
- if (map->l_serial != serial)
- result = -1;
- goto out;
-}
-
-static void
-internal_function
-_dl_debug_bindings (const char *undef_name, struct link_map *undef_map,
- const ElfW(Sym) **ref, struct sym_val *value,
- const struct r_found_version *version, int type_class,
- int protected);
-
-
-/* Search loaded objects' symbol tables for a definition of the symbol
- UNDEF_NAME, perhaps with a requested version for the symbol.
-
- We must never have calls to the audit functions inside this function
- or in any function which gets called. If this would happen the audit
- code might create a thread which can throw off all the scope locking. */
-lookup_t
-internal_function
-_dl_lookup_symbol_x (const char *undef_name, struct link_map *undef_map,
- const ElfW(Sym) **ref,
- struct r_scope_elem *symbol_scope[],
- const struct r_found_version *version,
- int type_class, int flags, struct link_map *skip_map)
-{
- const uint_fast32_t new_hash = dl_new_hash (undef_name);
- unsigned long int old_hash = 0xffffffff;
- struct sym_val current_value = { NULL, NULL };
- struct r_scope_elem **scope = symbol_scope;
-
- bump_num_relocations ();
-
- /* No other flag than DL_LOOKUP_ADD_DEPENDENCY or DL_LOOKUP_GSCOPE_LOCK
- is allowed if we look up a versioned symbol. */
- assert (version == NULL
- || (flags & ~(DL_LOOKUP_ADD_DEPENDENCY | DL_LOOKUP_GSCOPE_LOCK))
- == 0);
-
- size_t i = 0;
- if (__glibc_unlikely (skip_map != NULL))
- /* Search the relevant loaded objects for a definition. */
- while ((*scope)->r_list[i] != skip_map)
- ++i;
-
- /* Search the relevant loaded objects for a definition. */
- for (size_t start = i; *scope != NULL; start = 0, ++scope)
- {
- int res = do_lookup_x (undef_name, new_hash, &old_hash, *ref,
- &current_value, *scope, start, version, flags,
- skip_map, type_class, undef_map);
- if (res > 0)
- break;
-
- if (__glibc_unlikely (res < 0) && skip_map == NULL)
- {
- /* Oh, oh. The file named in the relocation entry does not
- contain the needed symbol. This code is never reached
- for unversioned lookups. */
- assert (version != NULL);
- const char *reference_name = undef_map ? undef_map->l_name : "";
-
- /* XXX We cannot translate the message. */
- _dl_signal_cerror (0, DSO_FILENAME (reference_name),
- N_("relocation error"),
- make_string ("symbol ", undef_name, ", version ",
- version->name,
- " not defined in file ",
- version->filename,
- " with link time reference",
- res == -2
- ? " (no version symbols)" : ""));
- *ref = NULL;
- return 0;
- }
- }
-
- if (__glibc_unlikely (current_value.s == NULL))
- {
- if ((*ref == NULL || ELFW(ST_BIND) ((*ref)->st_info) != STB_WEAK)
- && !(GLRO(dl_debug_mask) & DL_DEBUG_UNUSED))
- {
- /* We could find no value for a strong reference. */
- const char *reference_name = undef_map ? undef_map->l_name : "";
- const char *versionstr = version ? ", version " : "";
- const char *versionname = (version && version->name
- ? version->name : "");
-
- /* XXX We cannot translate the message. */
- _dl_signal_cerror (0, DSO_FILENAME (reference_name),
- N_("symbol lookup error"),
- make_string ("undefined symbol: ", undef_name,
- versionstr, versionname));
- }
- *ref = NULL;
- return 0;
- }
-
- int protected = (*ref
- && ELFW(ST_VISIBILITY) ((*ref)->st_other) == STV_PROTECTED);
- if (__glibc_unlikely (protected != 0))
- {
- /* It is very tricky. We need to figure out what value to
- return for the protected symbol. */
- if (type_class == ELF_RTYPE_CLASS_PLT)
- {
- if (current_value.s != NULL && current_value.m != undef_map)
- {
- current_value.s = *ref;
- current_value.m = undef_map;
- }
- }
- else
- {
- struct sym_val protected_value = { NULL, NULL };
-
- for (scope = symbol_scope; *scope != NULL; i = 0, ++scope)
- if (do_lookup_x (undef_name, new_hash, &old_hash, *ref,
- &protected_value, *scope, i, version, flags,
- skip_map,
- (ELF_RTYPE_CLASS_EXTERN_PROTECTED_DATA
- && ELFW(ST_TYPE) ((*ref)->st_info) == STT_OBJECT
- && type_class == ELF_RTYPE_CLASS_EXTERN_PROTECTED_DATA)
- ? ELF_RTYPE_CLASS_EXTERN_PROTECTED_DATA
- : ELF_RTYPE_CLASS_PLT, NULL) != 0)
- break;
-
- if (protected_value.s != NULL && protected_value.m != undef_map)
- {
- current_value.s = *ref;
- current_value.m = undef_map;
- }
- }
- }
-
- /* We have to check whether this would bind UNDEF_MAP to an object
- in the global scope which was dynamically loaded. In this case
- we have to prevent the latter from being unloaded unless the
- UNDEF_MAP object is also unloaded. */
- if (__glibc_unlikely (current_value.m->l_type == lt_loaded)
- /* Don't do this for explicit lookups as opposed to implicit
- runtime lookups. */
- && (flags & DL_LOOKUP_ADD_DEPENDENCY) != 0
- /* Add UNDEF_MAP to the dependencies. */
- && add_dependency (undef_map, current_value.m, flags) < 0)
- /* Something went wrong. Perhaps the object we tried to reference
- was just removed. Try finding another definition. */
- return _dl_lookup_symbol_x (undef_name, undef_map, ref,
- (flags & DL_LOOKUP_GSCOPE_LOCK)
- ? undef_map->l_scope : symbol_scope,
- version, type_class, flags, skip_map);
-
- /* The object is used. */
- if (__glibc_unlikely (current_value.m->l_used == 0))
- current_value.m->l_used = 1;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask)
- & (DL_DEBUG_BINDINGS|DL_DEBUG_PRELINK)))
- _dl_debug_bindings (undef_name, undef_map, ref,
- &current_value, version, type_class, protected);
-
- *ref = current_value.s;
- return LOOKUP_VALUE (current_value.m);
-}
-
-
-/* Cache the location of MAP's hash table. */
-
-void
-internal_function
-_dl_setup_hash (struct link_map *map)
-{
- Elf_Symndx *hash;
-
- if (__glibc_likely (map->l_info[DT_ADDRTAGIDX (DT_GNU_HASH) + DT_NUM
- + DT_THISPROCNUM + DT_VERSIONTAGNUM
- + DT_EXTRANUM + DT_VALNUM] != NULL))
- {
- Elf32_Word *hash32
- = (void *) D_PTR (map, l_info[DT_ADDRTAGIDX (DT_GNU_HASH) + DT_NUM
- + DT_THISPROCNUM + DT_VERSIONTAGNUM
- + DT_EXTRANUM + DT_VALNUM]);
- map->l_nbuckets = *hash32++;
- Elf32_Word symbias = *hash32++;
- Elf32_Word bitmask_nwords = *hash32++;
- /* Must be a power of two. */
- assert ((bitmask_nwords & (bitmask_nwords - 1)) == 0);
- map->l_gnu_bitmask_idxbits = bitmask_nwords - 1;
- map->l_gnu_shift = *hash32++;
-
- map->l_gnu_bitmask = (ElfW(Addr) *) hash32;
- hash32 += __ELF_NATIVE_CLASS / 32 * bitmask_nwords;
-
- map->l_gnu_buckets = hash32;
- hash32 += map->l_nbuckets;
- map->l_gnu_chain_zero = hash32 - symbias;
- return;
- }
-
- if (!map->l_info[DT_HASH])
- return;
- hash = (void *) D_PTR (map, l_info[DT_HASH]);
-
- map->l_nbuckets = *hash++;
- /* Skip nchain. */
- hash++;
- map->l_buckets = hash;
- hash += map->l_nbuckets;
- map->l_chain = hash;
-}
-
-
-static void
-internal_function
-_dl_debug_bindings (const char *undef_name, struct link_map *undef_map,
- const ElfW(Sym) **ref, struct sym_val *value,
- const struct r_found_version *version, int type_class,
- int protected)
-{
- const char *reference_name = undef_map->l_name;
-
- if (GLRO(dl_debug_mask) & DL_DEBUG_BINDINGS)
- {
- _dl_debug_printf ("binding file %s [%lu] to %s [%lu]: %s symbol `%s'",
- DSO_FILENAME (reference_name),
- undef_map->l_ns,
- DSO_FILENAME (value->m->l_name),
- value->m->l_ns,
- protected ? "protected" : "normal", undef_name);
- if (version)
- _dl_debug_printf_c (" [%s]\n", version->name);
- else
- _dl_debug_printf_c ("\n");
- }
-#ifdef SHARED
- if (GLRO(dl_debug_mask) & DL_DEBUG_PRELINK)
- {
-/* ELF_RTYPE_CLASS_XXX must match RTYPE_CLASS_XXX used by prelink with
- LD_TRACE_PRELINKING. */
-#define RTYPE_CLASS_VALID 8
-#define RTYPE_CLASS_PLT (8|1)
-#define RTYPE_CLASS_COPY (8|2)
-#define RTYPE_CLASS_TLS (8|4)
-#if ELF_RTYPE_CLASS_PLT != 0 && ELF_RTYPE_CLASS_PLT != 1
-# error ELF_RTYPE_CLASS_PLT must be 0 or 1!
-#endif
-#if ELF_RTYPE_CLASS_COPY != 0 && ELF_RTYPE_CLASS_COPY != 2
-# error ELF_RTYPE_CLASS_COPY must be 0 or 2!
-#endif
- int conflict = 0;
- struct sym_val val = { NULL, NULL };
-
- if ((GLRO(dl_trace_prelink_map) == NULL
- || GLRO(dl_trace_prelink_map) == GL(dl_ns)[LM_ID_BASE]._ns_loaded)
- && undef_map != GL(dl_ns)[LM_ID_BASE]._ns_loaded)
- {
- const uint_fast32_t new_hash = dl_new_hash (undef_name);
- unsigned long int old_hash = 0xffffffff;
- struct unique_sym *saved_entries
- = GL(dl_ns)[LM_ID_BASE]._ns_unique_sym_table.entries;
-
- GL(dl_ns)[LM_ID_BASE]._ns_unique_sym_table.entries = NULL;
- do_lookup_x (undef_name, new_hash, &old_hash, *ref, &val,
- undef_map->l_local_scope[0], 0, version, 0, NULL,
- type_class, undef_map);
- if (val.s != value->s || val.m != value->m)
- conflict = 1;
- else if (__glibc_unlikely (undef_map->l_symbolic_in_local_scope)
- && val.s
- && __glibc_unlikely (ELFW(ST_BIND) (val.s->st_info)
- == STB_GNU_UNIQUE))
- {
- /* If it is STB_GNU_UNIQUE and undef_map's l_local_scope
- contains any DT_SYMBOLIC libraries, unfortunately there
- can be conflicts even if the above is equal. As symbol
- resolution goes from the last library to the first and
- if a STB_GNU_UNIQUE symbol is found in some late DT_SYMBOLIC
- library, it would be the one that is looked up. */
- struct sym_val val2 = { NULL, NULL };
- size_t n;
- struct r_scope_elem *scope = undef_map->l_local_scope[0];
-
- for (n = 0; n < scope->r_nlist; n++)
- if (scope->r_list[n] == val.m)
- break;
-
- for (n++; n < scope->r_nlist; n++)
- if (scope->r_list[n]->l_info[DT_SYMBOLIC] != NULL
- && do_lookup_x (undef_name, new_hash, &old_hash, *ref,
- &val2,
- &scope->r_list[n]->l_symbolic_searchlist,
- 0, version, 0, NULL, type_class,
- undef_map) > 0)
- {
- conflict = 1;
- val = val2;
- break;
- }
- }
- GL(dl_ns)[LM_ID_BASE]._ns_unique_sym_table.entries = saved_entries;
- }
-
- if (value->s)
- {
- /* Keep only ELF_RTYPE_CLASS_PLT and ELF_RTYPE_CLASS_COPY
- bits since since prelink only uses them. */
- type_class &= ELF_RTYPE_CLASS_PLT | ELF_RTYPE_CLASS_COPY;
- if (__glibc_unlikely (ELFW(ST_TYPE) (value->s->st_info)
- == STT_TLS))
- /* Clear the RTYPE_CLASS_VALID bit in RTYPE_CLASS_TLS. */
- type_class = RTYPE_CLASS_TLS & ~RTYPE_CLASS_VALID;
- else if (__glibc_unlikely (ELFW(ST_TYPE) (value->s->st_info)
- == STT_GNU_IFUNC))
- /* Set the RTYPE_CLASS_VALID bit. */
- type_class |= RTYPE_CLASS_VALID;
- }
-
- if (conflict
- || GLRO(dl_trace_prelink_map) == undef_map
- || GLRO(dl_trace_prelink_map) == NULL
- || type_class >= 4)
- {
- _dl_printf ("%s 0x%0*Zx 0x%0*Zx -> 0x%0*Zx 0x%0*Zx ",
- conflict ? "conflict" : "lookup",
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) undef_map->l_map_start,
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) (((ElfW(Addr)) *ref) - undef_map->l_map_start),
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) (value->s ? value->m->l_map_start : 0),
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) (value->s ? value->s->st_value : 0));
-
- if (conflict)
- _dl_printf ("x 0x%0*Zx 0x%0*Zx ",
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) (val.s ? val.m->l_map_start : 0),
- (int) sizeof (ElfW(Addr)) * 2,
- (size_t) (val.s ? val.s->st_value : 0));
-
- _dl_printf ("/%x %s\n", type_class, undef_name);
- }
- }
-#endif
-}
diff --git a/elf/dl-machine-reject-phdr.h b/elf/dl-machine-reject-phdr.h
deleted file mode 100644
index 57253deb52..0000000000
--- a/elf/dl-machine-reject-phdr.h
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Machine-dependent program header inspection for the ELF loader.
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _DL_MACHINE_REJECT_PHDR_H
-#define _DL_MACHINE_REJECT_PHDR_H 1
-
-#include <stdbool.h>
-
-/* Return true iff ELF program headers are incompatible with the running
- host. */
-static inline bool
-elf_machine_reject_phdr_p (const ElfW(Phdr) *phdr, uint_fast16_t phnum,
- const char *buf, size_t len, struct link_map *map,
- int fd)
-{
- return false;
-}
-
-#endif /* dl-machine-reject-phdr.h */
diff --git a/elf/dl-map-segments.h b/elf/dl-map-segments.h
deleted file mode 100644
index d36f9bd2f6..0000000000
--- a/elf/dl-map-segments.h
+++ /dev/null
@@ -1,157 +0,0 @@
-/* Map in a shared object's segments. Generic version.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dl-load.h>
-
-/* This implementation assumes (as does the corresponding implementation
- of _dl_unmap_segments, in dl-unmap-segments.h) that shared objects
- are always laid out with all segments contiguous (or with gaps
- between them small enough that it's preferable to reserve all whole
- pages inside the gaps with PROT_NONE mappings rather than permitting
- other use of those parts of the address space). */
-
-static __always_inline const char *
-_dl_map_segments (struct link_map *l, int fd,
- const ElfW(Ehdr) *header, int type,
- const struct loadcmd loadcmds[], size_t nloadcmds,
- const size_t maplength, bool has_holes,
- struct link_map *loader)
-{
- const struct loadcmd *c = loadcmds;
-
- if (__glibc_likely (type == ET_DYN))
- {
- /* This is a position-independent shared object. We can let the
- kernel map it anywhere it likes, but we must have space for all
- the segments in their specified positions relative to the first.
- So we map the first segment without MAP_FIXED, but with its
- extent increased to cover all the segments. Then we remove
- access from excess portion, and there is known sufficient space
- there to remap from the later segments.
-
- As a refinement, sometimes we have an address that we would
- prefer to map such objects at; but this is only a preference,
- the OS can do whatever it likes. */
- ElfW(Addr) mappref
- = (ELF_PREFERRED_ADDRESS (loader, maplength,
- c->mapstart & GLRO(dl_use_load_bias))
- - MAP_BASE_ADDR (l));
-
- /* Remember which part of the address space this object uses. */
- l->l_map_start = (ElfW(Addr)) __mmap ((void *) mappref, maplength,
- c->prot,
- MAP_COPY|MAP_FILE,
- fd, c->mapoff);
- if (__glibc_unlikely ((void *) l->l_map_start == MAP_FAILED))
- return DL_MAP_SEGMENTS_ERROR_MAP_SEGMENT;
-
- l->l_map_end = l->l_map_start + maplength;
- l->l_addr = l->l_map_start - c->mapstart;
-
- if (has_holes)
- {
- /* Change protection on the excess portion to disallow all access;
- the portions we do not remap later will be inaccessible as if
- unallocated. Then jump into the normal segment-mapping loop to
- handle the portion of the segment past the end of the file
- mapping. */
- if (__glibc_unlikely
- (__mprotect ((caddr_t) (l->l_addr + c->mapend),
- loadcmds[nloadcmds - 1].mapstart - c->mapend,
- PROT_NONE) < 0))
- return DL_MAP_SEGMENTS_ERROR_MPROTECT;
- }
-
- l->l_contiguous = 1;
-
- goto postmap;
- }
-
- /* Remember which part of the address space this object uses. */
- l->l_map_start = c->mapstart + l->l_addr;
- l->l_map_end = l->l_map_start + maplength;
- l->l_contiguous = !has_holes;
-
- while (c < &loadcmds[nloadcmds])
- {
- if (c->mapend > c->mapstart
- /* Map the segment contents from the file. */
- && (__mmap ((void *) (l->l_addr + c->mapstart),
- c->mapend - c->mapstart, c->prot,
- MAP_FIXED|MAP_COPY|MAP_FILE,
- fd, c->mapoff)
- == MAP_FAILED))
- return DL_MAP_SEGMENTS_ERROR_MAP_SEGMENT;
-
- postmap:
- _dl_postprocess_loadcmd (l, header, c);
-
- if (c->allocend > c->dataend)
- {
- /* Extra zero pages should appear at the end of this segment,
- after the data mapped from the file. */
- ElfW(Addr) zero, zeroend, zeropage;
-
- zero = l->l_addr + c->dataend;
- zeroend = l->l_addr + c->allocend;
- zeropage = ((zero + GLRO(dl_pagesize) - 1)
- & ~(GLRO(dl_pagesize) - 1));
-
- if (zeroend < zeropage)
- /* All the extra data is in the last page of the segment.
- We can just zero it. */
- zeropage = zeroend;
-
- if (zeropage > zero)
- {
- /* Zero the final part of the last page of the segment. */
- if (__glibc_unlikely ((c->prot & PROT_WRITE) == 0))
- {
- /* Dag nab it. */
- if (__mprotect ((caddr_t) (zero
- & ~(GLRO(dl_pagesize) - 1)),
- GLRO(dl_pagesize), c->prot|PROT_WRITE) < 0)
- return DL_MAP_SEGMENTS_ERROR_MPROTECT;
- }
- memset ((void *) zero, '\0', zeropage - zero);
- if (__glibc_unlikely ((c->prot & PROT_WRITE) == 0))
- __mprotect ((caddr_t) (zero & ~(GLRO(dl_pagesize) - 1)),
- GLRO(dl_pagesize), c->prot);
- }
-
- if (zeroend > zeropage)
- {
- /* Map the remaining zero pages in from the zero fill FD. */
- caddr_t mapat;
- mapat = __mmap ((caddr_t) zeropage, zeroend - zeropage,
- c->prot, MAP_ANON|MAP_PRIVATE|MAP_FIXED,
- -1, 0);
- if (__glibc_unlikely (mapat == MAP_FAILED))
- return DL_MAP_SEGMENTS_ERROR_MAP_ZERO_FILL;
- }
- }
-
- ++c;
- }
-
- /* Notify ELF_PREFERRED_ADDRESS that we have to load this one
- fixed. */
- ELF_FIXED_ADDRESS (loader, c->mapstart);
-
- return NULL;
-}
diff --git a/elf/dl-minimal.c b/elf/dl-minimal.c
deleted file mode 100644
index 1a35baff2e..0000000000
--- a/elf/dl-minimal.c
+++ /dev/null
@@ -1,380 +0,0 @@
-/* Minimal replacements for basic facilities used in the dynamic linker.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <limits.h>
-#include <stdio.h>
-#include <string.h>
-#include <tls.h>
-#include <unistd.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/types.h>
-#include <ldsodefs.h>
-#include <_itoa.h>
-#include <malloc/malloc-internal.h>
-
-#include <assert.h>
-
-/* Minimal malloc allocator for used during initial link. After the
- initial link, a full malloc implementation is interposed, either
- the one in libc, or a different one supplied by the user through
- interposition. */
-
-static void *alloc_ptr, *alloc_end, *alloc_last_block;
-
-/* Declarations of global functions. */
-extern void weak_function free (void *ptr);
-extern void * weak_function realloc (void *ptr, size_t n);
-extern unsigned long int weak_function __strtoul_internal (const char *nptr,
- char **endptr,
- int base,
- int group);
-extern unsigned long int weak_function strtoul (const char *nptr,
- char **endptr, int base);
-
-
-/* Allocate an aligned memory block. */
-void * weak_function
-malloc (size_t n)
-{
- if (alloc_end == 0)
- {
- /* Consume any unused space in the last page of our data segment. */
- extern int _end attribute_hidden;
- alloc_ptr = &_end;
- alloc_end = (void *) 0 + (((alloc_ptr - (void *) 0)
- + GLRO(dl_pagesize) - 1)
- & ~(GLRO(dl_pagesize) - 1));
- }
-
- /* Make sure the allocation pointer is ideally aligned. */
- alloc_ptr = (void *) 0 + (((alloc_ptr - (void *) 0) + MALLOC_ALIGNMENT - 1)
- & ~(MALLOC_ALIGNMENT - 1));
-
- if (alloc_ptr + n >= alloc_end || n >= -(uintptr_t) alloc_ptr)
- {
- /* Insufficient space left; allocate another page plus one extra
- page to reduce number of mmap calls. */
- caddr_t page;
- size_t nup = (n + GLRO(dl_pagesize) - 1) & ~(GLRO(dl_pagesize) - 1);
- if (__glibc_unlikely (nup == 0 && n != 0))
- return NULL;
- nup += GLRO(dl_pagesize);
- page = __mmap (0, nup, PROT_READ|PROT_WRITE,
- MAP_ANON|MAP_PRIVATE, -1, 0);
- if (page == MAP_FAILED)
- return NULL;
- if (page != alloc_end)
- alloc_ptr = page;
- alloc_end = page + nup;
- }
-
- alloc_last_block = (void *) alloc_ptr;
- alloc_ptr += n;
- return alloc_last_block;
-}
-
-/* We use this function occasionally since the real implementation may
- be optimized when it can assume the memory it returns already is
- set to NUL. */
-void * weak_function
-calloc (size_t nmemb, size_t size)
-{
- /* New memory from the trivial malloc above is always already cleared.
- (We make sure that's true in the rare occasion it might not be,
- by clearing memory in free, below.) */
- size_t bytes = nmemb * size;
-
-#define HALF_SIZE_T (((size_t) 1) << (8 * sizeof (size_t) / 2))
- if (__builtin_expect ((nmemb | size) >= HALF_SIZE_T, 0)
- && size != 0 && bytes / size != nmemb)
- return NULL;
-
- return malloc (bytes);
-}
-
-/* This will rarely be called. */
-void weak_function
-free (void *ptr)
-{
- /* We can free only the last block allocated. */
- if (ptr == alloc_last_block)
- {
- /* Since this is rare, we clear the freed block here
- so that calloc can presume malloc returns cleared memory. */
- memset (alloc_last_block, '\0', alloc_ptr - alloc_last_block);
- alloc_ptr = alloc_last_block;
- }
-}
-
-/* This is only called with the most recent block returned by malloc. */
-void * weak_function
-realloc (void *ptr, size_t n)
-{
- if (ptr == NULL)
- return malloc (n);
- assert (ptr == alloc_last_block);
- size_t old_size = alloc_ptr - alloc_last_block;
- alloc_ptr = alloc_last_block;
- void *new = malloc (n);
- return new != ptr ? memcpy (new, ptr, old_size) : new;
-}
-
-/* Avoid signal frobnication in setjmp/longjmp. Keeps things smaller. */
-
-#include <setjmp.h>
-
-int weak_function
-__sigjmp_save (sigjmp_buf env, int savemask __attribute__ ((unused)))
-{
- env[0].__mask_was_saved = 0;
- return 0;
-}
-
-/* Define our own version of the internal function used by strerror. We
- only provide the messages for some common errors. This avoids pulling
- in the whole error list. */
-
-char * weak_function
-__strerror_r (int errnum, char *buf, size_t buflen)
-{
- char *msg;
-
- switch (errnum)
- {
- case ENOMEM:
- msg = (char *) "Cannot allocate memory";
- break;
- case EINVAL:
- msg = (char *) "Invalid argument";
- break;
- case ENOENT:
- msg = (char *) "No such file or directory";
- break;
- case EPERM:
- msg = (char *) "Operation not permitted";
- break;
- case EIO:
- msg = (char *) "Input/output error";
- break;
- case EACCES:
- msg = (char *) "Permission denied";
- break;
- default:
- /* No need to check buffer size, all calls in the dynamic linker
- provide enough space. */
- buf[buflen - 1] = '\0';
- msg = _itoa (errnum, buf + buflen - 1, 10, 0);
- msg = memcpy (msg - (sizeof ("Error ") - 1), "Error ",
- sizeof ("Error ") - 1);
- break;
- }
-
- return msg;
-}
-
-void
-__libc_fatal (const char *message)
-{
- _dl_fatal_printf ("%s", message);
-}
-rtld_hidden_def (__libc_fatal)
-
-void
-__attribute__ ((noreturn))
-__chk_fail (void)
-{
- _exit (127);
-}
-rtld_hidden_def (__chk_fail)
-
-#ifndef NDEBUG
-/* Define (weakly) our own assert failure function which doesn't use stdio.
- If we are linked into the user program (-ldl), the normal __assert_fail
- defn can override this one. */
-
-void weak_function
-__assert_fail (const char *assertion,
- const char *file, unsigned int line, const char *function)
-{
- _dl_fatal_printf ("\
-Inconsistency detected by ld.so: %s: %u: %s%sAssertion `%s' failed!\n",
- file, line, function ?: "", function ? ": " : "",
- assertion);
-
-}
-rtld_hidden_weak (__assert_fail)
-
-void weak_function
-__assert_perror_fail (int errnum,
- const char *file, unsigned int line,
- const char *function)
-{
- char errbuf[400];
- _dl_fatal_printf ("\
-Inconsistency detected by ld.so: %s: %u: %s%sUnexpected error: %s.\n",
- file, line, function ?: "", function ? ": " : "",
- __strerror_r (errnum, errbuf, sizeof errbuf));
-
-}
-rtld_hidden_weak (__assert_perror_fail)
-#endif
-
-unsigned long int weak_function
-__strtoul_internal (const char *nptr, char **endptr, int base, int group)
-{
- unsigned long int result = 0;
- long int sign = 1;
- unsigned max_digit;
-
- while (*nptr == ' ' || *nptr == '\t')
- ++nptr;
-
- if (*nptr == '-')
- {
- sign = -1;
- ++nptr;
- }
- else if (*nptr == '+')
- ++nptr;
-
- if (*nptr < '0' || *nptr > '9')
- {
- if (endptr != NULL)
- *endptr = (char *) nptr;
- return 0UL;
- }
-
- assert (base == 0);
- base = 10;
- max_digit = 9;
- if (*nptr == '0')
- {
- if (nptr[1] == 'x' || nptr[1] == 'X')
- {
- base = 16;
- nptr += 2;
- }
- else
- {
- base = 8;
- max_digit = 7;
- }
- }
-
- while (1)
- {
- unsigned long int digval;
- if (*nptr >= '0' && *nptr <= '0' + max_digit)
- digval = *nptr - '0';
- else if (base == 16)
- {
- if (*nptr >= 'a' && *nptr <= 'f')
- digval = *nptr - 'a' + 10;
- else if (*nptr >= 'A' && *nptr <= 'F')
- digval = *nptr - 'A' + 10;
- else
- break;
- }
- else
- break;
-
- if (result > ULONG_MAX / base
- || (result == ULONG_MAX / base && digval > ULONG_MAX % base))
- {
- errno = ERANGE;
- if (endptr != NULL)
- *endptr = (char *) nptr;
- return ULONG_MAX;
- }
- result *= base;
- result += digval;
- ++nptr;
- }
-
- if (endptr != NULL)
- *endptr = (char *) nptr;
- return result * sign;
-}
-
-
-#undef _itoa
-/* We always use _itoa instead of _itoa_word in ld.so since the former
- also has to be present and it is never about speed when these
- functions are used. */
-char *
-_itoa (unsigned long long int value, char *buflim, unsigned int base,
- int upper_case)
-{
- assert (! upper_case);
-
- do
- *--buflim = _itoa_lower_digits[value % base];
- while ((value /= base) != 0);
-
- return buflim;
-}
-
-/* The '_itoa_lower_digits' variable in libc.so is able to handle bases
- up to 36. We don't need this here. */
-const char _itoa_lower_digits[16] = "0123456789abcdef";
-rtld_hidden_data_def (_itoa_lower_digits)
-
-/* The following is not a complete strsep implementation. It cannot
- handle empty delimiter strings. But this isn't necessary for the
- execution of ld.so. */
-#undef strsep
-#undef __strsep
-char *
-__strsep (char **stringp, const char *delim)
-{
- char *begin;
-
- assert (delim[0] != '\0');
-
- begin = *stringp;
- if (begin != NULL)
- {
- char *end = begin;
-
- while (*end != '\0' || (end = NULL))
- {
- const char *dp = delim;
-
- do
- if (*dp == *end)
- break;
- while (*++dp != '\0');
-
- if (*dp != '\0')
- {
- *end++ = '\0';
- break;
- }
-
- ++end;
- }
-
- *stringp = end;
- }
-
- return begin;
-}
-weak_alias (__strsep, strsep)
-strong_alias (__strsep, __strsep_g)
diff --git a/elf/dl-misc.c b/elf/dl-misc.c
deleted file mode 100644
index c5d3e0e7c5..0000000000
--- a/elf/dl-misc.c
+++ /dev/null
@@ -1,362 +0,0 @@
-/* Miscellaneous support functions for dynamic linker
- Copyright (C) 1997-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <fcntl.h>
-#include <ldsodefs.h>
-#include <limits.h>
-#include <link.h>
-#include <stdarg.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdint.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-#include <sys/uio.h>
-#include <sysdep.h>
-#include <_itoa.h>
-#include <dl-writev.h>
-
-
-/* Read the whole contents of FILE into new mmap'd space with given
- protections. *SIZEP gets the size of the file. On error MAP_FAILED
- is returned. */
-
-void *
-internal_function
-_dl_sysdep_read_whole_file (const char *file, size_t *sizep, int prot)
-{
- void *result = MAP_FAILED;
- struct stat64 st;
- int fd = __open (file, O_RDONLY | O_CLOEXEC);
- if (fd >= 0)
- {
- if (__fxstat64 (_STAT_VER, fd, &st) >= 0)
- {
- *sizep = st.st_size;
-
- /* No need to map the file if it is empty. */
- if (*sizep != 0)
- /* Map a copy of the file contents. */
- result = __mmap (NULL, *sizep, prot,
-#ifdef MAP_COPY
- MAP_COPY
-#else
- MAP_PRIVATE
-#endif
-#ifdef MAP_FILE
- | MAP_FILE
-#endif
- , fd, 0);
- }
- __close (fd);
- }
- return result;
-}
-
-
-/* Bare-bones printf implementation. This function only knows about
- the formats and flags needed and can handle only up to 64 stripes in
- the output. */
-static void
-_dl_debug_vdprintf (int fd, int tag_p, const char *fmt, va_list arg)
-{
-# define NIOVMAX 64
- struct iovec iov[NIOVMAX];
- int niov = 0;
- pid_t pid = 0;
- char pidbuf[12];
-
- while (*fmt != '\0')
- {
- const char *startp = fmt;
-
- if (tag_p > 0)
- {
- /* Generate the tag line once. It consists of the PID and a
- colon followed by a tab. */
- if (pid == 0)
- {
- char *p;
- pid = __getpid ();
- assert (pid >= 0 && sizeof (pid_t) <= 4);
- p = _itoa (pid, &pidbuf[10], 10, 0);
- while (p > pidbuf)
- *--p = ' ';
- pidbuf[10] = ':';
- pidbuf[11] = '\t';
- }
-
- /* Append to the output. */
- assert (niov < NIOVMAX);
- iov[niov].iov_len = 12;
- iov[niov++].iov_base = pidbuf;
-
- /* No more tags until we see the next newline. */
- tag_p = -1;
- }
-
- /* Skip everything except % and \n (if tags are needed). */
- while (*fmt != '\0' && *fmt != '%' && (! tag_p || *fmt != '\n'))
- ++fmt;
-
- /* Append constant string. */
- assert (niov < NIOVMAX);
- if ((iov[niov].iov_len = fmt - startp) != 0)
- iov[niov++].iov_base = (char *) startp;
-
- if (*fmt == '%')
- {
- /* It is a format specifier. */
- char fill = ' ';
- int width = -1;
- int prec = -1;
-#if LONG_MAX != INT_MAX
- int long_mod = 0;
-#endif
-
- /* Recognize zero-digit fill flag. */
- if (*++fmt == '0')
- {
- fill = '0';
- ++fmt;
- }
-
- /* See whether with comes from a parameter. Note that no other
- way to specify the width is implemented. */
- if (*fmt == '*')
- {
- width = va_arg (arg, int);
- ++fmt;
- }
-
- /* Handle precision. */
- if (*fmt == '.' && fmt[1] == '*')
- {
- prec = va_arg (arg, int);
- fmt += 2;
- }
-
- /* Recognize the l modifier. It is only important on some
- platforms where long and int have a different size. We
- can use the same code for size_t. */
- if (*fmt == 'l' || *fmt == 'Z')
- {
-#if LONG_MAX != INT_MAX
- long_mod = 1;
-#endif
- ++fmt;
- }
-
- switch (*fmt)
- {
- /* Integer formatting. */
- case 'u':
- case 'x':
- {
- /* We have to make a difference if long and int have a
- different size. */
-#if LONG_MAX != INT_MAX
- unsigned long int num = (long_mod
- ? va_arg (arg, unsigned long int)
- : va_arg (arg, unsigned int));
-#else
- unsigned long int num = va_arg (arg, unsigned int);
-#endif
- /* We use alloca() to allocate the buffer with the most
- pessimistic guess for the size. Using alloca() allows
- having more than one integer formatting in a call. */
- char *buf = (char *) alloca (3 * sizeof (unsigned long int));
- char *endp = &buf[3 * sizeof (unsigned long int)];
- char *cp = _itoa (num, endp, *fmt == 'x' ? 16 : 10, 0);
-
- /* Pad to the width the user specified. */
- if (width != -1)
- while (endp - cp < width)
- *--cp = fill;
-
- iov[niov].iov_base = cp;
- iov[niov].iov_len = endp - cp;
- ++niov;
- }
- break;
-
- case 's':
- /* Get the string argument. */
- iov[niov].iov_base = va_arg (arg, char *);
- iov[niov].iov_len = strlen (iov[niov].iov_base);
- if (prec != -1)
- iov[niov].iov_len = MIN ((size_t) prec, iov[niov].iov_len);
- ++niov;
- break;
-
- case '%':
- iov[niov].iov_base = (void *) fmt;
- iov[niov].iov_len = 1;
- ++niov;
- break;
-
- default:
- assert (! "invalid format specifier");
- }
- ++fmt;
- }
- else if (*fmt == '\n')
- {
- /* See whether we have to print a single newline character. */
- if (fmt == startp)
- {
- iov[niov].iov_base = (char *) startp;
- iov[niov++].iov_len = 1;
- }
- else
- /* No, just add it to the rest of the string. */
- ++iov[niov - 1].iov_len;
-
- /* Next line, print a tag again. */
- tag_p = 1;
- ++fmt;
- }
- }
-
- /* Finally write the result. */
- _dl_writev (fd, iov, niov);
-}
-
-
-/* Write to debug file. */
-void
-_dl_debug_printf (const char *fmt, ...)
-{
- va_list arg;
-
- va_start (arg, fmt);
- _dl_debug_vdprintf (GLRO(dl_debug_fd), 1, fmt, arg);
- va_end (arg);
-}
-
-
-/* Write to debug file but don't start with a tag. */
-void
-_dl_debug_printf_c (const char *fmt, ...)
-{
- va_list arg;
-
- va_start (arg, fmt);
- _dl_debug_vdprintf (GLRO(dl_debug_fd), -1, fmt, arg);
- va_end (arg);
-}
-
-
-/* Write the given file descriptor. */
-void
-_dl_dprintf (int fd, const char *fmt, ...)
-{
- va_list arg;
-
- va_start (arg, fmt);
- _dl_debug_vdprintf (fd, 0, fmt, arg);
- va_end (arg);
-}
-
-
-/* Test whether given NAME matches any of the names of the given object. */
-int
-internal_function
-_dl_name_match_p (const char *name, const struct link_map *map)
-{
- if (strcmp (name, map->l_name) == 0)
- return 1;
-
- struct libname_list *runp = map->l_libname;
-
- while (runp != NULL)
- if (strcmp (name, runp->name) == 0)
- return 1;
- else
- runp = runp->next;
-
- return 0;
-}
-
-
-unsigned long int
-internal_function
-_dl_higher_prime_number (unsigned long int n)
-{
- /* These are primes that are near, but slightly smaller than, a
- power of two. */
- static const uint32_t primes[] = {
- UINT32_C (7),
- UINT32_C (13),
- UINT32_C (31),
- UINT32_C (61),
- UINT32_C (127),
- UINT32_C (251),
- UINT32_C (509),
- UINT32_C (1021),
- UINT32_C (2039),
- UINT32_C (4093),
- UINT32_C (8191),
- UINT32_C (16381),
- UINT32_C (32749),
- UINT32_C (65521),
- UINT32_C (131071),
- UINT32_C (262139),
- UINT32_C (524287),
- UINT32_C (1048573),
- UINT32_C (2097143),
- UINT32_C (4194301),
- UINT32_C (8388593),
- UINT32_C (16777213),
- UINT32_C (33554393),
- UINT32_C (67108859),
- UINT32_C (134217689),
- UINT32_C (268435399),
- UINT32_C (536870909),
- UINT32_C (1073741789),
- UINT32_C (2147483647),
- /* 4294967291L */
- UINT32_C (2147483647) + UINT32_C (2147483644)
- };
-
- const uint32_t *low = &primes[0];
- const uint32_t *high = &primes[sizeof (primes) / sizeof (primes[0])];
-
- while (low != high)
- {
- const uint32_t *mid = low + (high - low) / 2;
- if (n > *mid)
- low = mid + 1;
- else
- high = mid;
- }
-
-#if 0
- /* If we've run out of primes, abort. */
- if (n > *low)
- {
- fprintf (stderr, "Cannot find prime bigger than %lu\n", n);
- abort ();
- }
-#endif
-
- return *low;
-}
diff --git a/elf/dl-object.c b/elf/dl-object.c
deleted file mode 100644
index 4c43235148..0000000000
--- a/elf/dl-object.c
+++ /dev/null
@@ -1,229 +0,0 @@
-/* Storage management for the chain of loaded shared objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <string.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-
-#include <assert.h>
-
-
-/* Add the new link_map NEW to the end of the namespace list. */
-void
-internal_function
-_dl_add_to_namespace_list (struct link_map *new, Lmid_t nsid)
-{
- /* We modify the list of loaded objects. */
- __rtld_lock_lock_recursive (GL(dl_load_write_lock));
-
- if (GL(dl_ns)[nsid]._ns_loaded != NULL)
- {
- struct link_map *l = GL(dl_ns)[nsid]._ns_loaded;
- while (l->l_next != NULL)
- l = l->l_next;
- new->l_prev = l;
- /* new->l_next = NULL; Would be necessary but we use calloc. */
- l->l_next = new;
- }
- else
- GL(dl_ns)[nsid]._ns_loaded = new;
- ++GL(dl_ns)[nsid]._ns_nloaded;
- new->l_serial = GL(dl_load_adds);
- ++GL(dl_load_adds);
-
- __rtld_lock_unlock_recursive (GL(dl_load_write_lock));
-}
-
-
-/* Allocate a `struct link_map' for a new object being loaded,
- and enter it into the _dl_loaded list. */
-struct link_map *
-internal_function
-_dl_new_object (char *realname, const char *libname, int type,
- struct link_map *loader, int mode, Lmid_t nsid)
-{
- size_t libname_len = strlen (libname) + 1;
- struct link_map *new;
- struct libname_list *newname;
-#ifdef SHARED
- /* We create the map for the executable before we know whether we have
- auditing libraries and if yes, how many. Assume the worst. */
- unsigned int naudit = GLRO(dl_naudit) ?: ((mode & __RTLD_OPENEXEC)
- ? DL_NNS : 0);
- size_t audit_space = naudit * sizeof (new->l_audit[0]);
-#else
-# define audit_space 0
-#endif
-
- new = (struct link_map *) calloc (sizeof (*new) + audit_space
- + sizeof (struct link_map *)
- + sizeof (*newname) + libname_len, 1);
- if (new == NULL)
- return NULL;
-
- new->l_real = new;
- new->l_symbolic_searchlist.r_list = (struct link_map **) ((char *) (new + 1)
- + audit_space);
-
- new->l_libname = newname
- = (struct libname_list *) (new->l_symbolic_searchlist.r_list + 1);
- newname->name = (char *) memcpy (newname + 1, libname, libname_len);
- /* newname->next = NULL; We use calloc therefore not necessary. */
- newname->dont_free = 1;
-
- /* When we create the executable link map, or a VDSO link map, we start
- with "" for the l_name. In these cases "" points to ld.so rodata
- and won't get dumped during core file generation. Therefore to assist
- gdb and to create more self-contained core files we adjust l_name to
- point at the newly allocated copy (which will get dumped) instead of
- the ld.so rodata copy. */
- new->l_name = *realname ? realname : (char *) newname->name + libname_len - 1;
- new->l_type = type;
- /* If we set the bit now since we know it is never used we avoid
- dirtying the cache line later. */
- if ((GLRO(dl_debug_mask) & DL_DEBUG_UNUSED) == 0)
- new->l_used = 1;
- new->l_loader = loader;
-#if NO_TLS_OFFSET != 0
- new->l_tls_offset = NO_TLS_OFFSET;
-#endif
- new->l_ns = nsid;
-
-#ifdef SHARED
- for (unsigned int cnt = 0; cnt < naudit; ++cnt)
- {
- new->l_audit[cnt].cookie = (uintptr_t) new;
- /* new->l_audit[cnt].bindflags = 0; */
- }
-#endif
-
- /* new->l_global = 0; We use calloc therefore not necessary. */
-
- /* Use the 'l_scope_mem' array by default for the 'l_scope'
- information. If we need more entries we will allocate a large
- array dynamically. */
- new->l_scope = new->l_scope_mem;
- new->l_scope_max = sizeof (new->l_scope_mem) / sizeof (new->l_scope_mem[0]);
-
- /* Counter for the scopes we have to handle. */
- int idx = 0;
-
- if (GL(dl_ns)[nsid]._ns_loaded != NULL)
- /* Add the global scope. */
- new->l_scope[idx++] = &GL(dl_ns)[nsid]._ns_loaded->l_searchlist;
-
- /* If we have no loader the new object acts as it. */
- if (loader == NULL)
- loader = new;
- else
- /* Determine the local scope. */
- while (loader->l_loader != NULL)
- loader = loader->l_loader;
-
- /* Insert the scope if it isn't the global scope we already added. */
- if (idx == 0 || &loader->l_searchlist != new->l_scope[0])
- {
- if ((mode & RTLD_DEEPBIND) != 0 && idx != 0)
- {
- new->l_scope[1] = new->l_scope[0];
- idx = 0;
- }
-
- new->l_scope[idx] = &loader->l_searchlist;
- }
-
- new->l_local_scope[0] = &new->l_searchlist;
-
- /* Don't try to find the origin for the main map which has the name "". */
- if (realname[0] != '\0')
- {
- size_t realname_len = strlen (realname) + 1;
- char *origin;
- char *cp;
-
- if (realname[0] == '/')
- {
- /* It is an absolute path. Use it. But we have to make a
- copy since we strip out the trailing slash. */
- cp = origin = (char *) malloc (realname_len);
- if (origin == NULL)
- {
- origin = (char *) -1;
- goto out;
- }
- }
- else
- {
- size_t len = realname_len;
- char *result = NULL;
-
- /* Get the current directory name. */
- origin = NULL;
- do
- {
- char *new_origin;
-
- len += 128;
- new_origin = (char *) realloc (origin, len);
- if (new_origin == NULL)
- /* We exit the loop. Note that result == NULL. */
- break;
- origin = new_origin;
- }
- while ((result = __getcwd (origin, len - realname_len)) == NULL
- && errno == ERANGE);
-
- if (result == NULL)
- {
- /* We were not able to determine the current directory.
- Note that free(origin) is OK if origin == NULL. */
- free (origin);
- origin = (char *) -1;
- goto out;
- }
-
- /* Find the end of the path and see whether we have to add a
- slash. We could use rawmemchr but this need not be
- fast. */
- cp = (strchr) (origin, '\0');
- if (cp[-1] != '/')
- *cp++ = '/';
- }
-
- /* Add the real file name. */
- cp = __mempcpy (cp, realname, realname_len);
-
- /* Now remove the filename and the slash. Leave the slash if
- the name is something like "/foo". */
- do
- --cp;
- while (*cp != '/');
-
- if (cp == origin)
- /* Keep the only slash which is the first character. */
- ++cp;
- *cp = '\0';
-
- out:
- new->l_origin = origin;
- }
-
- return new;
-}
diff --git a/elf/dl-open.c b/elf/dl-open.c
deleted file mode 100644
index cec54db413..0000000000
--- a/elf/dl-open.c
+++ /dev/null
@@ -1,737 +0,0 @@
-/* Load a shared object at runtime, relocate it, and run its initializer.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <dlfcn.h>
-#include <errno.h>
-#include <libintl.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/mman.h> /* Check whether MAP_COPY is defined. */
-#include <sys/param.h>
-#include <libc-lock.h>
-#include <ldsodefs.h>
-#include <caller.h>
-#include <sysdep-cancel.h>
-#include <tls.h>
-#include <stap-probe.h>
-#include <atomic.h>
-
-#include <dl-dst.h>
-
-
-extern int __libc_multiple_libcs; /* Defined in init-first.c. */
-
-/* We must be careful not to leave us in an inconsistent state. Thus we
- catch any error and re-raise it after cleaning up. */
-
-struct dl_open_args
-{
- const char *file;
- int mode;
- /* This is the caller of the dlopen() function. */
- const void *caller_dlopen;
- /* This is the caller of _dl_open(). */
- const void *caller_dl_open;
- struct link_map *map;
- /* Namespace ID. */
- Lmid_t nsid;
- /* Original parameters to the program and the current environment. */
- int argc;
- char **argv;
- char **env;
-};
-
-
-static int
-add_to_global (struct link_map *new)
-{
- struct link_map **new_global;
- unsigned int to_add = 0;
- unsigned int cnt;
-
- /* Count the objects we have to put in the global scope. */
- for (cnt = 0; cnt < new->l_searchlist.r_nlist; ++cnt)
- if (new->l_searchlist.r_list[cnt]->l_global == 0)
- ++to_add;
-
- /* The symbols of the new objects and its dependencies are to be
- introduced into the global scope that will be used to resolve
- references from other dynamically-loaded objects.
-
- The global scope is the searchlist in the main link map. We
- extend this list if necessary. There is one problem though:
- since this structure was allocated very early (before the libc
- is loaded) the memory it uses is allocated by the malloc()-stub
- in the ld.so. When we come here these functions are not used
- anymore. Instead the malloc() implementation of the libc is
- used. But this means the block from the main map cannot be used
- in an realloc() call. Therefore we allocate a completely new
- array the first time we have to add something to the locale scope. */
-
- struct link_namespaces *ns = &GL(dl_ns)[new->l_ns];
- if (ns->_ns_global_scope_alloc == 0)
- {
- /* This is the first dynamic object given global scope. */
- ns->_ns_global_scope_alloc
- = ns->_ns_main_searchlist->r_nlist + to_add + 8;
- new_global = (struct link_map **)
- malloc (ns->_ns_global_scope_alloc * sizeof (struct link_map *));
- if (new_global == NULL)
- {
- ns->_ns_global_scope_alloc = 0;
- nomem:
- _dl_signal_error (ENOMEM, new->l_libname->name, NULL,
- N_("cannot extend global scope"));
- return 1;
- }
-
- /* Copy over the old entries. */
- ns->_ns_main_searchlist->r_list
- = memcpy (new_global, ns->_ns_main_searchlist->r_list,
- (ns->_ns_main_searchlist->r_nlist
- * sizeof (struct link_map *)));
- }
- else if (ns->_ns_main_searchlist->r_nlist + to_add
- > ns->_ns_global_scope_alloc)
- {
- /* We have to extend the existing array of link maps in the
- main map. */
- struct link_map **old_global
- = GL(dl_ns)[new->l_ns]._ns_main_searchlist->r_list;
- size_t new_nalloc = ((ns->_ns_global_scope_alloc + to_add) * 2);
-
- new_global = (struct link_map **)
- malloc (new_nalloc * sizeof (struct link_map *));
- if (new_global == NULL)
- goto nomem;
-
- memcpy (new_global, old_global,
- ns->_ns_global_scope_alloc * sizeof (struct link_map *));
-
- ns->_ns_global_scope_alloc = new_nalloc;
- ns->_ns_main_searchlist->r_list = new_global;
-
- if (!RTLD_SINGLE_THREAD_P)
- THREAD_GSCOPE_WAIT ();
-
- free (old_global);
- }
-
- /* Now add the new entries. */
- unsigned int new_nlist = ns->_ns_main_searchlist->r_nlist;
- for (cnt = 0; cnt < new->l_searchlist.r_nlist; ++cnt)
- {
- struct link_map *map = new->l_searchlist.r_list[cnt];
-
- if (map->l_global == 0)
- {
- map->l_global = 1;
- ns->_ns_main_searchlist->r_list[new_nlist++] = map;
-
- /* We modify the global scope. Report this. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_SCOPES))
- _dl_debug_printf ("\nadd %s [%lu] to global scope\n",
- map->l_name, map->l_ns);
- }
- }
- atomic_write_barrier ();
- ns->_ns_main_searchlist->r_nlist = new_nlist;
-
- return 0;
-}
-
-/* Search link maps in all namespaces for the DSO that contains the object at
- address ADDR. Returns the pointer to the link map of the matching DSO, or
- NULL if a match is not found. */
-struct link_map *
-internal_function
-_dl_find_dso_for_object (const ElfW(Addr) addr)
-{
- struct link_map *l;
-
- /* Find the highest-addressed object that ADDR is not below. */
- for (Lmid_t ns = 0; ns < GL(dl_nns); ++ns)
- for (l = GL(dl_ns)[ns]._ns_loaded; l != NULL; l = l->l_next)
- if (addr >= l->l_map_start && addr < l->l_map_end
- && (l->l_contiguous
- || _dl_addr_inside_object (l, (ElfW(Addr)) addr)))
- {
- assert (ns == l->l_ns);
- return l;
- }
- return NULL;
-}
-rtld_hidden_def (_dl_find_dso_for_object);
-
-static void
-dl_open_worker (void *a)
-{
- struct dl_open_args *args = a;
- const char *file = args->file;
- int mode = args->mode;
- struct link_map *call_map = NULL;
-
- /* Check whether _dl_open() has been called from a valid DSO. */
- if (__check_caller (args->caller_dl_open,
- allow_libc|allow_libdl|allow_ldso) != 0)
- _dl_signal_error (0, "dlopen", NULL, N_("invalid caller"));
-
- /* Determine the caller's map if necessary. This is needed in case
- we have a DST, when we don't know the namespace ID we have to put
- the new object in, or when the file name has no path in which
- case we need to look along the RUNPATH/RPATH of the caller. */
- const char *dst = strchr (file, '$');
- if (dst != NULL || args->nsid == __LM_ID_CALLER
- || strchr (file, '/') == NULL)
- {
- const void *caller_dlopen = args->caller_dlopen;
-
- /* We have to find out from which object the caller is calling.
- By default we assume this is the main application. */
- call_map = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
-
- struct link_map *l = _dl_find_dso_for_object ((ElfW(Addr)) caller_dlopen);
-
- if (l)
- call_map = l;
-
- if (args->nsid == __LM_ID_CALLER)
- args->nsid = call_map->l_ns;
- }
-
- /* One might be tempted to assert that we are RT_CONSISTENT at this point, but that
- may not be true if this is a recursive call to dlopen. */
- _dl_debug_initialize (0, args->nsid);
-
- /* Load the named object. */
- struct link_map *new;
- args->map = new = _dl_map_object (call_map, file, lt_loaded, 0,
- mode | __RTLD_CALLMAP, args->nsid);
-
- /* If the pointer returned is NULL this means the RTLD_NOLOAD flag is
- set and the object is not already loaded. */
- if (new == NULL)
- {
- assert (mode & RTLD_NOLOAD);
- return;
- }
-
- /* Mark the object as not deletable if the RTLD_NODELETE flags was passed.
- Do this early so that we don't skip marking the object if it was
- already loaded. */
- if (__glibc_unlikely (mode & RTLD_NODELETE))
- new->l_flags_1 |= DF_1_NODELETE;
-
- if (__glibc_unlikely (mode & __RTLD_SPROF))
- /* This happens only if we load a DSO for 'sprof'. */
- return;
-
- /* This object is directly loaded. */
- ++new->l_direct_opencount;
-
- /* It was already open. */
- if (__glibc_unlikely (new->l_searchlist.r_list != NULL))
- {
- /* Let the user know about the opencount. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("opening file=%s [%lu]; direct_opencount=%u\n\n",
- new->l_name, new->l_ns, new->l_direct_opencount);
-
- /* If the user requested the object to be in the global namespace
- but it is not so far, add it now. */
- if ((mode & RTLD_GLOBAL) && new->l_global == 0)
- (void) add_to_global (new);
-
- assert (_dl_debug_initialize (0, args->nsid)->r_state == RT_CONSISTENT);
-
- return;
- }
-
- /* Load that object's dependencies. */
- _dl_map_object_deps (new, NULL, 0, 0,
- mode & (__RTLD_DLOPEN | RTLD_DEEPBIND | __RTLD_AUDIT));
-
- /* So far, so good. Now check the versions. */
- for (unsigned int i = 0; i < new->l_searchlist.r_nlist; ++i)
- if (new->l_searchlist.r_list[i]->l_real->l_versions == NULL)
- (void) _dl_check_map_versions (new->l_searchlist.r_list[i]->l_real,
- 0, 0);
-
-#ifdef SHARED
- /* Auditing checkpoint: we have added all objects. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- struct link_map *head = GL(dl_ns)[new->l_ns]._ns_loaded;
- /* Do not call the functions for any auditing object. */
- if (head->l_auditing == 0)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&head->l_audit[cnt].cookie, LA_ACT_CONSISTENT);
-
- afct = afct->next;
- }
- }
- }
-#endif
-
- /* Notify the debugger all new objects are now ready to go. */
- struct r_debug *r = _dl_debug_initialize (0, args->nsid);
- r->r_state = RT_CONSISTENT;
- _dl_debug_state ();
- LIBC_PROBE (map_complete, 3, args->nsid, r, new);
-
- /* Print scope information. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_SCOPES))
- _dl_show_scope (new, 0);
-
- /* Only do lazy relocation if `LD_BIND_NOW' is not set. */
- int reloc_mode = mode & __RTLD_AUDIT;
- if (GLRO(dl_lazy))
- reloc_mode |= mode & RTLD_LAZY;
-
- /* Sort the objects by dependency for the relocation process. This
- allows IFUNC relocations to work and it also means copy
- relocation of dependencies are if necessary overwritten. */
- size_t nmaps = 0;
- struct link_map *l = new;
- do
- {
- if (! l->l_real->l_relocated)
- ++nmaps;
- l = l->l_next;
- }
- while (l != NULL);
- struct link_map *maps[nmaps];
- nmaps = 0;
- l = new;
- do
- {
- if (! l->l_real->l_relocated)
- maps[nmaps++] = l;
- l = l->l_next;
- }
- while (l != NULL);
- if (nmaps > 1)
- {
- uint16_t seen[nmaps];
- memset (seen, '\0', sizeof (seen));
- size_t i = 0;
- while (1)
- {
- ++seen[i];
- struct link_map *thisp = maps[i];
-
- /* Find the last object in the list for which the current one is
- a dependency and move the current object behind the object
- with the dependency. */
- size_t k = nmaps - 1;
- while (k > i)
- {
- struct link_map **runp = maps[k]->l_initfini;
- if (runp != NULL)
- /* Look through the dependencies of the object. */
- while (*runp != NULL)
- if (__glibc_unlikely (*runp++ == thisp))
- {
- /* Move the current object to the back past the last
- object with it as the dependency. */
- memmove (&maps[i], &maps[i + 1],
- (k - i) * sizeof (maps[0]));
- maps[k] = thisp;
-
- if (seen[i + 1] > nmaps - i)
- {
- ++i;
- goto next_clear;
- }
-
- uint16_t this_seen = seen[i];
- memmove (&seen[i], &seen[i + 1],
- (k - i) * sizeof (seen[0]));
- seen[k] = this_seen;
-
- goto next;
- }
-
- --k;
- }
-
- if (++i == nmaps)
- break;
- next_clear:
- memset (&seen[i], 0, (nmaps - i) * sizeof (seen[0]));
- next:;
- }
- }
-
- int relocation_in_progress = 0;
-
- for (size_t i = nmaps; i-- > 0; )
- {
- l = maps[i];
-
- if (! relocation_in_progress)
- {
- /* Notify the debugger that relocations are about to happen. */
- LIBC_PROBE (reloc_start, 2, args->nsid, r);
- relocation_in_progress = 1;
- }
-
-#ifdef SHARED
- if (__glibc_unlikely (GLRO(dl_profile) != NULL))
- {
- /* If this here is the shared object which we want to profile
- make sure the profile is started. We can find out whether
- this is necessary or not by observing the `_dl_profile_map'
- variable. If it was NULL but is not NULL afterwards we must
- start the profiling. */
- struct link_map *old_profile_map = GL(dl_profile_map);
-
- _dl_relocate_object (l, l->l_scope, reloc_mode | RTLD_LAZY, 1);
-
- if (old_profile_map == NULL && GL(dl_profile_map) != NULL)
- {
- /* We must prepare the profiling. */
- _dl_start_profile ();
-
- /* Prevent unloading the object. */
- GL(dl_profile_map)->l_flags_1 |= DF_1_NODELETE;
- }
- }
- else
-#endif
- _dl_relocate_object (l, l->l_scope, reloc_mode, 0);
- }
-
- /* If the file is not loaded now as a dependency, add the search
- list of the newly loaded object to the scope. */
- bool any_tls = false;
- unsigned int first_static_tls = new->l_searchlist.r_nlist;
- for (unsigned int i = 0; i < new->l_searchlist.r_nlist; ++i)
- {
- struct link_map *imap = new->l_searchlist.r_list[i];
- int from_scope = 0;
-
- /* If the initializer has been called already, the object has
- not been loaded here and now. */
- if (imap->l_init_called && imap->l_type == lt_loaded)
- {
- struct r_scope_elem **runp = imap->l_scope;
- size_t cnt = 0;
-
- while (*runp != NULL)
- {
- if (*runp == &new->l_searchlist)
- break;
- ++cnt;
- ++runp;
- }
-
- if (*runp != NULL)
- /* Avoid duplicates. */
- continue;
-
- if (__glibc_unlikely (cnt + 1 >= imap->l_scope_max))
- {
- /* The 'r_scope' array is too small. Allocate a new one
- dynamically. */
- size_t new_size;
- struct r_scope_elem **newp;
-
-#define SCOPE_ELEMS(imap) \
- (sizeof (imap->l_scope_mem) / sizeof (imap->l_scope_mem[0]))
-
- if (imap->l_scope != imap->l_scope_mem
- && imap->l_scope_max < SCOPE_ELEMS (imap))
- {
- new_size = SCOPE_ELEMS (imap);
- newp = imap->l_scope_mem;
- }
- else
- {
- new_size = imap->l_scope_max * 2;
- newp = (struct r_scope_elem **)
- malloc (new_size * sizeof (struct r_scope_elem *));
- if (newp == NULL)
- _dl_signal_error (ENOMEM, "dlopen", NULL,
- N_("cannot create scope list"));
- }
-
- memcpy (newp, imap->l_scope, cnt * sizeof (imap->l_scope[0]));
- struct r_scope_elem **old = imap->l_scope;
-
- imap->l_scope = newp;
-
- if (old != imap->l_scope_mem)
- _dl_scope_free (old);
-
- imap->l_scope_max = new_size;
- }
-
- /* First terminate the extended list. Otherwise a thread
- might use the new last element and then use the garbage
- at offset IDX+1. */
- imap->l_scope[cnt + 1] = NULL;
- atomic_write_barrier ();
- imap->l_scope[cnt] = &new->l_searchlist;
-
- /* Print only new scope information. */
- from_scope = cnt;
- }
- /* Only add TLS memory if this object is loaded now and
- therefore is not yet initialized. */
- else if (! imap->l_init_called
- /* Only if the module defines thread local data. */
- && __builtin_expect (imap->l_tls_blocksize > 0, 0))
- {
- /* Now that we know the object is loaded successfully add
- modules containing TLS data to the slot info table. We
- might have to increase its size. */
- _dl_add_to_slotinfo (imap);
-
- if (imap->l_need_tls_init
- && first_static_tls == new->l_searchlist.r_nlist)
- first_static_tls = i;
-
- /* We have to bump the generation counter. */
- any_tls = true;
- }
-
- /* Print scope information. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_SCOPES))
- _dl_show_scope (imap, from_scope);
- }
-
- /* Bump the generation number if necessary. */
- if (any_tls && __builtin_expect (++GL(dl_tls_generation) == 0, 0))
- _dl_fatal_printf (N_("\
-TLS generation counter wrapped! Please report this."));
-
- /* We need a second pass for static tls data, because _dl_update_slotinfo
- must not be run while calls to _dl_add_to_slotinfo are still pending. */
- for (unsigned int i = first_static_tls; i < new->l_searchlist.r_nlist; ++i)
- {
- struct link_map *imap = new->l_searchlist.r_list[i];
-
- if (imap->l_need_tls_init
- && ! imap->l_init_called
- && imap->l_tls_blocksize > 0)
- {
- /* For static TLS we have to allocate the memory here and
- now, but we can delay updating the DTV. */
- imap->l_need_tls_init = 0;
-#ifdef SHARED
- /* Update the slot information data for at least the
- generation of the DSO we are allocating data for. */
- _dl_update_slotinfo (imap->l_tls_modid);
-#endif
-
- GL(dl_init_static_tls) (imap);
- assert (imap->l_need_tls_init == 0);
- }
- }
-
- /* Notify the debugger all new objects have been relocated. */
- if (relocation_in_progress)
- LIBC_PROBE (reloc_complete, 3, args->nsid, r, new);
-
-#ifndef SHARED
- DL_STATIC_INIT (new);
-#endif
-
- /* Run the initializer functions of new objects. */
- _dl_init (new, args->argc, args->argv, args->env);
-
- /* Now we can make the new map available in the global scope. */
- if (mode & RTLD_GLOBAL)
- /* Move the object in the global namespace. */
- if (add_to_global (new) != 0)
- /* It failed. */
- return;
-
-#ifndef SHARED
- /* We must be the static _dl_open in libc.a. A static program that
- has loaded a dynamic object now has competition. */
- __libc_multiple_libcs = 1;
-#endif
-
- /* Let the user know about the opencount. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_FILES))
- _dl_debug_printf ("opening file=%s [%lu]; direct_opencount=%u\n\n",
- new->l_name, new->l_ns, new->l_direct_opencount);
-}
-
-
-void *
-_dl_open (const char *file, int mode, const void *caller_dlopen, Lmid_t nsid,
- int argc, char *argv[], char *env[])
-{
- if ((mode & RTLD_BINDING_MASK) == 0)
- /* One of the flags must be set. */
- _dl_signal_error (EINVAL, file, NULL, N_("invalid mode for dlopen()"));
-
- /* Make sure we are alone. */
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- if (__glibc_unlikely (nsid == LM_ID_NEWLM))
- {
- /* Find a new namespace. */
- for (nsid = 1; DL_NNS > 1 && nsid < GL(dl_nns); ++nsid)
- if (GL(dl_ns)[nsid]._ns_loaded == NULL)
- break;
-
- if (__glibc_unlikely (nsid == DL_NNS))
- {
- /* No more namespace available. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- _dl_signal_error (EINVAL, file, NULL, N_("\
-no more namespaces available for dlmopen()"));
- }
- else if (nsid == GL(dl_nns))
- {
- __rtld_lock_initialize (GL(dl_ns)[nsid]._ns_unique_sym_table.lock);
- ++GL(dl_nns);
- }
-
- _dl_debug_initialize (0, nsid)->r_state = RT_CONSISTENT;
- }
- /* Never allow loading a DSO in a namespace which is empty. Such
- direct placements is only causing problems. Also don't allow
- loading into a namespace used for auditing. */
- else if (__glibc_unlikely (nsid != LM_ID_BASE && nsid != __LM_ID_CALLER)
- && (__glibc_unlikely (nsid < 0 || nsid >= GL(dl_nns))
- /* This prevents the [NSID] index expressions from being
- evaluated, so the compiler won't think that we are
- accessing an invalid index here in the !SHARED case where
- DL_NNS is 1 and so any NSID != 0 is invalid. */
- || DL_NNS == 1
- || GL(dl_ns)[nsid]._ns_nloaded == 0
- || GL(dl_ns)[nsid]._ns_loaded->l_auditing))
- _dl_signal_error (EINVAL, file, NULL,
- N_("invalid target namespace in dlmopen()"));
-
- struct dl_open_args args;
- args.file = file;
- args.mode = mode;
- args.caller_dlopen = caller_dlopen;
- args.caller_dl_open = RETURN_ADDRESS (0);
- args.map = NULL;
- args.nsid = nsid;
- args.argc = argc;
- args.argv = argv;
- args.env = env;
-
- const char *objname;
- const char *errstring;
- bool malloced;
- int errcode = _dl_catch_error (&objname, &errstring, &malloced,
- dl_open_worker, &args);
-
-#if defined USE_LDCONFIG && !defined MAP_COPY
- /* We must unmap the cache file. */
- _dl_unload_cache ();
-#endif
-
- /* See if an error occurred during loading. */
- if (__glibc_unlikely (errstring != NULL))
- {
- /* Remove the object from memory. It may be in an inconsistent
- state if relocation failed, for example. */
- if (args.map)
- {
- /* Maybe some of the modules which were loaded use TLS.
- Since it will be removed in the following _dl_close call
- we have to mark the dtv array as having gaps to fill the
- holes. This is a pessimistic assumption which won't hurt
- if not true. There is no need to do this when we are
- loading the auditing DSOs since TLS has not yet been set
- up. */
- if ((mode & __RTLD_AUDIT) == 0)
- GL(dl_tls_dtv_gaps) = true;
-
- _dl_close_worker (args.map, true);
- }
-
- assert (_dl_debug_initialize (0, args.nsid)->r_state == RT_CONSISTENT);
-
- /* Release the lock. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- /* Make a local copy of the error string so that we can release the
- memory allocated for it. */
- size_t len_errstring = strlen (errstring) + 1;
- char *local_errstring;
- if (objname == errstring + len_errstring)
- {
- size_t total_len = len_errstring + strlen (objname) + 1;
- local_errstring = alloca (total_len);
- memcpy (local_errstring, errstring, total_len);
- objname = local_errstring + len_errstring;
- }
- else
- {
- local_errstring = alloca (len_errstring);
- memcpy (local_errstring, errstring, len_errstring);
- }
-
- if (malloced)
- free ((char *) errstring);
-
- /* Reraise the error. */
- _dl_signal_error (errcode, objname, NULL, local_errstring);
- }
-
- assert (_dl_debug_initialize (0, args.nsid)->r_state == RT_CONSISTENT);
-
- /* Release the lock. */
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- return args.map;
-}
-
-
-void
-_dl_show_scope (struct link_map *l, int from)
-{
- _dl_debug_printf ("object=%s [%lu]\n",
- DSO_FILENAME (l->l_name), l->l_ns);
- if (l->l_scope != NULL)
- for (int scope_cnt = from; l->l_scope[scope_cnt] != NULL; ++scope_cnt)
- {
- _dl_debug_printf (" scope %u:", scope_cnt);
-
- for (unsigned int cnt = 0; cnt < l->l_scope[scope_cnt]->r_nlist; ++cnt)
- if (*l->l_scope[scope_cnt]->r_list[cnt]->l_name)
- _dl_debug_printf_c (" %s",
- l->l_scope[scope_cnt]->r_list[cnt]->l_name);
- else
- _dl_debug_printf_c (" %s", RTLD_PROGNAME);
-
- _dl_debug_printf_c ("\n");
- }
- else
- _dl_debug_printf (" no scope\n");
- _dl_debug_printf ("\n");
-}
diff --git a/elf/dl-origin.c b/elf/dl-origin.c
deleted file mode 100644
index 1e44272a8e..0000000000
--- a/elf/dl-origin.c
+++ /dev/null
@@ -1,50 +0,0 @@
-/* Find path of executable.
- Copyright (C) 1998-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@cygnus.com>, 1998.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdlib.h>
-#include <string.h>
-#include <sys/param.h>
-#include <ldsodefs.h>
-
-#include <dl-dst.h>
-
-
-const char *
-_dl_get_origin (void)
-{
- char *result = (char *) -1;
- /* We use the environment variable LD_ORIGIN_PATH. If it is set make
- a copy and strip out trailing slashes. */
- if (GLRO(dl_origin_path) != NULL)
- {
- size_t len = strlen (GLRO(dl_origin_path));
- result = (char *) malloc (len + 1);
- if (result == NULL)
- result = (char *) -1;
- else
- {
- char *cp = __mempcpy (result, GLRO(dl_origin_path), len);
- while (cp > result + 1 && cp[-1] == '/')
- --cp;
- *cp = '\0';
- }
- }
-
- return result;
-}
diff --git a/elf/dl-profile.c b/elf/dl-profile.c
deleted file mode 100644
index a4f11089a1..0000000000
--- a/elf/dl-profile.c
+++ /dev/null
@@ -1,596 +0,0 @@
-/* Profiling of shared libraries.
- Copyright (C) 1997-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
- Based on the BSD mcount implementation.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <inttypes.h>
-#include <limits.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdint.h>
-#include <ldsodefs.h>
-#include <sys/gmon.h>
-#include <sys/gmon_out.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-#include <atomic.h>
-
-/* The LD_PROFILE feature has to be implemented different to the
- normal profiling using the gmon/ functions. The problem is that an
- arbitrary amount of processes simulataneously can be run using
- profiling and all write the results in the same file. To provide
- this mechanism one could implement a complicated mechanism to merge
- the content of two profiling runs or one could extend the file
- format to allow more than one data set. For the second solution we
- would have the problem that the file can grow in size beyond any
- limit and both solutions have the problem that the concurrency of
- writing the results is a big problem.
-
- Another much simpler method is to use mmap to map the same file in
- all using programs and modify the data in the mmap'ed area and so
- also automatically on the disk. Using the MAP_SHARED option of
- mmap(2) this can be done without big problems in more than one
- file.
-
- This approach is very different from the normal profiling. We have
- to use the profiling data in exactly the way they are expected to
- be written to disk. But the normal format used by gprof is not usable
- to do this. It is optimized for size. It writes the tags as single
- bytes but this means that the following 32/64 bit values are
- unaligned.
-
- Therefore we use a new format. This will look like this
-
- 0 1 2 3 <- byte is 32 bit word
- 0000 g m o n
- 0004 *version* <- GMON_SHOBJ_VERSION
- 0008 00 00 00 00
- 000c 00 00 00 00
- 0010 00 00 00 00
-
- 0014 *tag* <- GMON_TAG_TIME_HIST
- 0018 ?? ?? ?? ??
- ?? ?? ?? ?? <- 32/64 bit LowPC
- 0018+A ?? ?? ?? ??
- ?? ?? ?? ?? <- 32/64 bit HighPC
- 0018+2*A *histsize*
- 001c+2*A *profrate*
- 0020+2*A s e c o
- 0024+2*A n d s \0
- 0028+2*A \0 \0 \0 \0
- 002c+2*A \0 \0 \0
- 002f+2*A s
-
- 0030+2*A ?? ?? ?? ?? <- Count data
- ... ...
- 0030+2*A+K ?? ?? ?? ??
-
- 0030+2*A+K *tag* <- GMON_TAG_CG_ARC
- 0034+2*A+K *lastused*
- 0038+2*A+K ?? ?? ?? ??
- ?? ?? ?? ?? <- FromPC#1
- 0038+3*A+K ?? ?? ?? ??
- ?? ?? ?? ?? <- ToPC#1
- 0038+4*A+K ?? ?? ?? ?? <- Count#1
- ... ... ...
- 0038+(2*(CN-1)+2)*A+(CN-1)*4+K ?? ?? ?? ??
- ?? ?? ?? ?? <- FromPC#CGN
- 0038+(2*(CN-1)+3)*A+(CN-1)*4+K ?? ?? ?? ??
- ?? ?? ?? ?? <- ToPC#CGN
- 0038+(2*CN+2)*A+(CN-1)*4+K ?? ?? ?? ?? <- Count#CGN
-
- We put (for now?) no basic block information in the file since this would
- introduce rase conditions among all the processes who want to write them.
-
- `K' is the number of count entries which is computed as
-
- textsize / HISTFRACTION
-
- `CG' in the above table is the number of call graph arcs. Normally,
- the table is sparse and the profiling code writes out only the those
- entries which are really used in the program run. But since we must
- not extend this table (the profiling file) we'll keep them all here.
- So CN can be executed in advance as
-
- MINARCS <= textsize*(ARCDENSITY/100) <= MAXARCS
-
- Now the remaining question is: how to build the data structures we can
- work with from this data. We need the from set and must associate the
- froms with all the associated tos. We will do this by constructing this
- data structures at the program start. To do this we'll simply visit all
- entries in the call graph table and add it to the appropriate list. */
-
-extern int __profile_frequency (void);
-libc_hidden_proto (__profile_frequency)
-
-/* We define a special type to address the elements of the arc table.
- This is basically the `gmon_cg_arc_record' format but it includes
- the room for the tag and it uses real types. */
-struct here_cg_arc_record
- {
- uintptr_t from_pc;
- uintptr_t self_pc;
- /* The count field is atomically incremented in _dl_mcount, which
- requires it to be properly aligned for its type, and for this
- alignment to be visible to the compiler. The amount of data
- before an array of this structure is calculated as
- expected_size in _dl_start_profile. Everything in that
- calculation is a multiple of 4 bytes (in the case of
- kcountsize, because it is derived from a subtraction of
- page-aligned values, and the corresponding calculation in
- __monstartup also ensures it is at least a multiple of the size
- of u_long), so all copies of this field do in fact have the
- appropriate alignment. */
- uint32_t count __attribute__ ((aligned (__alignof__ (uint32_t))));
- } __attribute__ ((packed));
-
-static struct here_cg_arc_record *data;
-
-/* Nonzero if profiling is under way. */
-static int running;
-
-/* This is the number of entry which have been incorporated in the toset. */
-static uint32_t narcs;
-/* This is a pointer to the object representing the number of entries
- currently in the mmaped file. At no point of time this has to be the
- same as NARCS. If it is equal all entries from the file are in our
- lists. */
-static volatile uint32_t *narcsp;
-
-
-struct here_fromstruct
- {
- struct here_cg_arc_record volatile *here;
- uint16_t link;
- };
-
-static volatile uint16_t *tos;
-
-static struct here_fromstruct *froms;
-static uint32_t fromlimit;
-static volatile uint32_t fromidx;
-
-static uintptr_t lowpc;
-static size_t textsize;
-static unsigned int log_hashfraction;
-
-
-
-/* Set up profiling data to profile object desribed by MAP. The output
- file is found (or created) in OUTPUT_DIR. */
-void
-internal_function
-_dl_start_profile (void)
-{
- char *filename;
- int fd;
- struct stat64 st;
- const ElfW(Phdr) *ph;
- ElfW(Addr) mapstart = ~((ElfW(Addr)) 0);
- ElfW(Addr) mapend = 0;
- char *hist, *cp;
- size_t idx;
- size_t tossize;
- size_t fromssize;
- uintptr_t highpc;
- uint16_t *kcount;
- size_t kcountsize;
- struct gmon_hdr *addr = NULL;
- off_t expected_size;
- /* See profil(2) where this is described. */
- int s_scale;
-#define SCALE_1_TO_1 0x10000L
- const char *errstr = NULL;
-
- /* Compute the size of the sections which contain program code. */
- for (ph = GL(dl_profile_map)->l_phdr;
- ph < &GL(dl_profile_map)->l_phdr[GL(dl_profile_map)->l_phnum]; ++ph)
- if (ph->p_type == PT_LOAD && (ph->p_flags & PF_X))
- {
- ElfW(Addr) start = (ph->p_vaddr & ~(GLRO(dl_pagesize) - 1));
- ElfW(Addr) end = ((ph->p_vaddr + ph->p_memsz + GLRO(dl_pagesize) - 1)
- & ~(GLRO(dl_pagesize) - 1));
-
- if (start < mapstart)
- mapstart = start;
- if (end > mapend)
- mapend = end;
- }
-
- /* Now we can compute the size of the profiling data. This is done
- with the same formulars as in `monstartup' (see gmon.c). */
- running = 0;
- lowpc = ROUNDDOWN (mapstart + GL(dl_profile_map)->l_addr,
- HISTFRACTION * sizeof (HISTCOUNTER));
- highpc = ROUNDUP (mapend + GL(dl_profile_map)->l_addr,
- HISTFRACTION * sizeof (HISTCOUNTER));
- textsize = highpc - lowpc;
- kcountsize = textsize / HISTFRACTION;
- if ((HASHFRACTION & (HASHFRACTION - 1)) == 0)
- {
- /* If HASHFRACTION is a power of two, mcount can use shifting
- instead of integer division. Precompute shift amount.
-
- This is a constant but the compiler cannot compile the
- expression away since the __ffs implementation is not known
- to the compiler. Help the compiler by precomputing the
- usual cases. */
- assert (HASHFRACTION == 2);
-
- if (sizeof (*froms) == 8)
- log_hashfraction = 4;
- else if (sizeof (*froms) == 16)
- log_hashfraction = 5;
- else
- log_hashfraction = __ffs (HASHFRACTION * sizeof (*froms)) - 1;
- }
- else
- log_hashfraction = -1;
- tossize = textsize / HASHFRACTION;
- fromlimit = textsize * ARCDENSITY / 100;
- if (fromlimit < MINARCS)
- fromlimit = MINARCS;
- if (fromlimit > MAXARCS)
- fromlimit = MAXARCS;
- fromssize = fromlimit * sizeof (struct here_fromstruct);
-
- expected_size = (sizeof (struct gmon_hdr)
- + 4 + sizeof (struct gmon_hist_hdr) + kcountsize
- + 4 + 4 + fromssize * sizeof (struct here_cg_arc_record));
-
- /* Create the gmon_hdr we expect or write. */
- struct real_gmon_hdr
- {
- char cookie[4];
- int32_t version;
- char spare[3 * 4];
- } gmon_hdr;
- if (sizeof (gmon_hdr) != sizeof (struct gmon_hdr)
- || (offsetof (struct real_gmon_hdr, cookie)
- != offsetof (struct gmon_hdr, cookie))
- || (offsetof (struct real_gmon_hdr, version)
- != offsetof (struct gmon_hdr, version)))
- abort ();
-
- memcpy (&gmon_hdr.cookie[0], GMON_MAGIC, sizeof (gmon_hdr.cookie));
- gmon_hdr.version = GMON_SHOBJ_VERSION;
- memset (gmon_hdr.spare, '\0', sizeof (gmon_hdr.spare));
-
- /* Create the hist_hdr we expect or write. */
- struct real_gmon_hist_hdr
- {
- char *low_pc;
- char *high_pc;
- int32_t hist_size;
- int32_t prof_rate;
- char dimen[15];
- char dimen_abbrev;
- } hist_hdr;
- if (sizeof (hist_hdr) != sizeof (struct gmon_hist_hdr)
- || (offsetof (struct real_gmon_hist_hdr, low_pc)
- != offsetof (struct gmon_hist_hdr, low_pc))
- || (offsetof (struct real_gmon_hist_hdr, high_pc)
- != offsetof (struct gmon_hist_hdr, high_pc))
- || (offsetof (struct real_gmon_hist_hdr, hist_size)
- != offsetof (struct gmon_hist_hdr, hist_size))
- || (offsetof (struct real_gmon_hist_hdr, prof_rate)
- != offsetof (struct gmon_hist_hdr, prof_rate))
- || (offsetof (struct real_gmon_hist_hdr, dimen)
- != offsetof (struct gmon_hist_hdr, dimen))
- || (offsetof (struct real_gmon_hist_hdr, dimen_abbrev)
- != offsetof (struct gmon_hist_hdr, dimen_abbrev)))
- abort ();
-
- hist_hdr.low_pc = (char *) mapstart;
- hist_hdr.high_pc = (char *) mapend;
- hist_hdr.hist_size = kcountsize / sizeof (HISTCOUNTER);
- hist_hdr.prof_rate = __profile_frequency ();
- if (sizeof (hist_hdr.dimen) >= sizeof ("seconds"))
- {
- memcpy (hist_hdr.dimen, "seconds", sizeof ("seconds"));
- memset (hist_hdr.dimen + sizeof ("seconds"), '\0',
- sizeof (hist_hdr.dimen) - sizeof ("seconds"));
- }
- else
- strncpy (hist_hdr.dimen, "seconds", sizeof (hist_hdr.dimen));
- hist_hdr.dimen_abbrev = 's';
-
- /* First determine the output name. We write in the directory
- OUTPUT_DIR and the name is composed from the shared objects
- soname (or the file name) and the ending ".profile". */
- filename = (char *) alloca (strlen (GLRO(dl_profile_output)) + 1
- + strlen (GLRO(dl_profile)) + sizeof ".profile");
- cp = __stpcpy (filename, GLRO(dl_profile_output));
- *cp++ = '/';
- __stpcpy (__stpcpy (cp, GLRO(dl_profile)), ".profile");
-
- fd = __open (filename, O_RDWR | O_CREAT | O_NOFOLLOW, DEFFILEMODE);
- if (fd == -1)
- {
- char buf[400];
- int errnum;
-
- /* We cannot write the profiling data so don't do anything. */
- errstr = "%s: cannot open file: %s\n";
- print_error:
- errnum = errno;
- if (fd != -1)
- __close (fd);
- _dl_error_printf (errstr, filename,
- __strerror_r (errnum, buf, sizeof buf));
- return;
- }
-
- if (__fxstat64 (_STAT_VER, fd, &st) < 0 || !S_ISREG (st.st_mode))
- {
- /* Not stat'able or not a regular file => don't use it. */
- errstr = "%s: cannot stat file: %s\n";
- goto print_error;
- }
-
- /* Test the size. If it does not match what we expect from the size
- values in the map MAP we don't use it and warn the user. */
- if (st.st_size == 0)
- {
- /* We have to create the file. */
- char buf[GLRO(dl_pagesize)];
-
- memset (buf, '\0', GLRO(dl_pagesize));
-
- if (__lseek (fd, expected_size & ~(GLRO(dl_pagesize) - 1), SEEK_SET) == -1)
- {
- cannot_create:
- errstr = "%s: cannot create file: %s\n";
- goto print_error;
- }
-
- if (TEMP_FAILURE_RETRY (__libc_write (fd, buf, (expected_size
- & (GLRO(dl_pagesize)
- - 1))))
- < 0)
- goto cannot_create;
- }
- else if (st.st_size != expected_size)
- {
- __close (fd);
- wrong_format:
-
- if (addr != NULL)
- __munmap ((void *) addr, expected_size);
-
- _dl_error_printf ("%s: file is no correct profile data file for `%s'\n",
- filename, GLRO(dl_profile));
- return;
- }
-
- addr = (struct gmon_hdr *) __mmap (NULL, expected_size, PROT_READ|PROT_WRITE,
- MAP_SHARED|MAP_FILE, fd, 0);
- if (addr == (struct gmon_hdr *) MAP_FAILED)
- {
- errstr = "%s: cannot map file: %s\n";
- goto print_error;
- }
-
- /* We don't need the file descriptor anymore. */
- __close (fd);
-
- /* Pointer to data after the header. */
- hist = (char *) (addr + 1);
- kcount = (uint16_t *) ((char *) hist + sizeof (uint32_t)
- + sizeof (struct gmon_hist_hdr));
-
- /* Compute pointer to array of the arc information. */
- narcsp = (uint32_t *) ((char *) kcount + kcountsize + sizeof (uint32_t));
- data = (struct here_cg_arc_record *) ((char *) narcsp + sizeof (uint32_t));
-
- if (st.st_size == 0)
- {
- /* Create the signature. */
- memcpy (addr, &gmon_hdr, sizeof (struct gmon_hdr));
-
- *(uint32_t *) hist = GMON_TAG_TIME_HIST;
- memcpy (hist + sizeof (uint32_t), &hist_hdr,
- sizeof (struct gmon_hist_hdr));
-
- narcsp[-1] = GMON_TAG_CG_ARC;
- }
- else
- {
- /* Test the signature in the file. */
- if (memcmp (addr, &gmon_hdr, sizeof (struct gmon_hdr)) != 0
- || *(uint32_t *) hist != GMON_TAG_TIME_HIST
- || memcmp (hist + sizeof (uint32_t), &hist_hdr,
- sizeof (struct gmon_hist_hdr)) != 0
- || narcsp[-1] != GMON_TAG_CG_ARC)
- goto wrong_format;
- }
-
- /* Allocate memory for the froms data and the pointer to the tos records. */
- tos = (uint16_t *) calloc (tossize + fromssize, 1);
- if (tos == NULL)
- {
- __munmap ((void *) addr, expected_size);
- _dl_fatal_printf ("Out of memory while initializing profiler\n");
- /* NOTREACHED */
- }
-
- froms = (struct here_fromstruct *) ((char *) tos + tossize);
- fromidx = 0;
-
- /* Now we have to process all the arc count entries. BTW: it is
- not critical whether the *NARCSP value changes meanwhile. Before
- we enter a new entry in to toset we will check that everything is
- available in TOS. This happens in _dl_mcount.
-
- Loading the entries in reverse order should help to get the most
- frequently used entries at the front of the list. */
- for (idx = narcs = MIN (*narcsp, fromlimit); idx > 0; )
- {
- size_t to_index;
- size_t newfromidx;
- --idx;
- to_index = (data[idx].self_pc / (HASHFRACTION * sizeof (*tos)));
- newfromidx = fromidx++;
- froms[newfromidx].here = &data[idx];
- froms[newfromidx].link = tos[to_index];
- tos[to_index] = newfromidx;
- }
-
- /* Setup counting data. */
- if (kcountsize < highpc - lowpc)
- {
-#if 0
- s_scale = ((double) kcountsize / (highpc - lowpc)) * SCALE_1_TO_1;
-#else
- size_t range = highpc - lowpc;
- size_t quot = range / kcountsize;
-
- if (quot >= SCALE_1_TO_1)
- s_scale = 1;
- else if (quot >= SCALE_1_TO_1 / 256)
- s_scale = SCALE_1_TO_1 / quot;
- else if (range > ULONG_MAX / 256)
- s_scale = (SCALE_1_TO_1 * 256) / (range / (kcountsize / 256));
- else
- s_scale = (SCALE_1_TO_1 * 256) / ((range * 256) / kcountsize);
-#endif
- }
- else
- s_scale = SCALE_1_TO_1;
-
- /* Start the profiler. */
- __profil ((void *) kcount, kcountsize, lowpc, s_scale);
-
- /* Turn on profiling. */
- running = 1;
-}
-
-
-void
-_dl_mcount (ElfW(Addr) frompc, ElfW(Addr) selfpc)
-{
- volatile uint16_t *topcindex;
- size_t i, fromindex;
- struct here_fromstruct *fromp;
-
- if (! running)
- return;
-
- /* Compute relative addresses. The shared object can be loaded at
- any address. The value of frompc could be anything. We cannot
- restrict it in any way, just set to a fixed value (0) in case it
- is outside the allowed range. These calls show up as calls from
- <external> in the gprof output. */
- frompc -= lowpc;
- if (frompc >= textsize)
- frompc = 0;
- selfpc -= lowpc;
- if (selfpc >= textsize)
- goto done;
-
- /* Getting here we now have to find out whether the location was
- already used. If yes we are lucky and only have to increment a
- counter (this also has to be atomic). If the entry is new things
- are getting complicated... */
-
- /* Avoid integer divide if possible. */
- if ((HASHFRACTION & (HASHFRACTION - 1)) == 0)
- i = selfpc >> log_hashfraction;
- else
- i = selfpc / (HASHFRACTION * sizeof (*tos));
-
- topcindex = &tos[i];
- fromindex = *topcindex;
-
- if (fromindex == 0)
- goto check_new_or_add;
-
- fromp = &froms[fromindex];
-
- /* We have to look through the chain of arcs whether there is already
- an entry for our arc. */
- while (fromp->here->from_pc != frompc)
- {
- if (fromp->link != 0)
- do
- fromp = &froms[fromp->link];
- while (fromp->link != 0 && fromp->here->from_pc != frompc);
-
- if (fromp->here->from_pc != frompc)
- {
- topcindex = &fromp->link;
-
- check_new_or_add:
- /* Our entry is not among the entries we read so far from the
- data file. Now see whether we have to update the list. */
- while (narcs != *narcsp && narcs < fromlimit)
- {
- size_t to_index;
- size_t newfromidx;
- to_index = (data[narcs].self_pc
- / (HASHFRACTION * sizeof (*tos)));
- newfromidx = catomic_exchange_and_add (&fromidx, 1) + 1;
- froms[newfromidx].here = &data[narcs];
- froms[newfromidx].link = tos[to_index];
- tos[to_index] = newfromidx;
- catomic_increment (&narcs);
- }
-
- /* If we still have no entry stop searching and insert. */
- if (*topcindex == 0)
- {
- uint_fast32_t newarc = catomic_exchange_and_add (narcsp, 1);
-
- /* In rare cases it could happen that all entries in FROMS are
- occupied. So we cannot count this anymore. */
- if (newarc >= fromlimit)
- goto done;
-
- *topcindex = catomic_exchange_and_add (&fromidx, 1) + 1;
- fromp = &froms[*topcindex];
-
- fromp->here = &data[newarc];
- data[newarc].from_pc = frompc;
- data[newarc].self_pc = selfpc;
- data[newarc].count = 0;
- fromp->link = 0;
- catomic_increment (&narcs);
-
- break;
- }
-
- fromp = &froms[*topcindex];
- }
- else
- /* Found in. */
- break;
- }
-
- /* Increment the counter. */
- catomic_increment (&fromp->here->count);
-
- done:
- ;
-}
-rtld_hidden_def (_dl_mcount)
diff --git a/elf/dl-profstub.c b/elf/dl-profstub.c
deleted file mode 100644
index 0915e29093..0000000000
--- a/elf/dl-profstub.c
+++ /dev/null
@@ -1,41 +0,0 @@
-/* Helper definitions for profiling of shared libraries.
- Copyright (C) 1998-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <elf.h>
-#include <ldsodefs.h>
-
-/* This is the map for the shared object we profile. It is defined here
- only because we test for this value being NULL or not. */
-
-
-void
-_dl_mcount_wrapper (void *selfpc)
-{
- GLRO(dl_mcount) ((ElfW(Addr)) RETURN_ADDRESS (0), (ElfW(Addr)) selfpc);
-}
-
-
-void
-_dl_mcount_wrapper_check (void *selfpc)
-{
- if (GL(dl_profile_map) != NULL)
- GLRO(dl_mcount) ((ElfW(Addr)) RETURN_ADDRESS (0), (ElfW(Addr)) selfpc);
-}
-libc_hidden_def (_dl_mcount_wrapper_check)
diff --git a/elf/dl-reloc.c b/elf/dl-reloc.c
deleted file mode 100644
index b3c3a9bbf9..0000000000
--- a/elf/dl-reloc.c
+++ /dev/null
@@ -1,363 +0,0 @@
-/* Relocate a shared object and resolve its references to other loaded objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <ldsodefs.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/types.h>
-#include <_itoa.h>
-#include <libc-pointer-arith.h>
-#include "dynamic-link.h"
-
-/* Statistics function. */
-#ifdef SHARED
-# define bump_num_cache_relocations() ++GL(dl_num_cache_relocations)
-#else
-# define bump_num_cache_relocations() ((void) 0)
-#endif
-
-
-/* We are trying to perform a static TLS relocation in MAP, but it was
- dynamically loaded. This can only work if there is enough surplus in
- the static TLS area already allocated for each running thread. If this
- object's TLS segment is too big to fit, we fail. If it fits,
- we set MAP->l_tls_offset and return.
- This function intentionally does not return any value but signals error
- directly, as static TLS should be rare and code handling it should
- not be inlined as much as possible. */
-int
-internal_function
-_dl_try_allocate_static_tls (struct link_map *map)
-{
- /* If we've already used the variable with dynamic access, or if the
- alignment requirements are too high, fail. */
- if (map->l_tls_offset == FORCED_DYNAMIC_TLS_OFFSET
- || map->l_tls_align > GL(dl_tls_static_align))
- {
- fail:
- return -1;
- }
-
-#if TLS_TCB_AT_TP
- size_t freebytes = GL(dl_tls_static_size) - GL(dl_tls_static_used);
- if (freebytes < TLS_TCB_SIZE)
- goto fail;
- freebytes -= TLS_TCB_SIZE;
-
- size_t blsize = map->l_tls_blocksize + map->l_tls_firstbyte_offset;
- if (freebytes < blsize)
- goto fail;
-
- size_t n = (freebytes - blsize) / map->l_tls_align;
-
- size_t offset = GL(dl_tls_static_used) + (freebytes - n * map->l_tls_align
- - map->l_tls_firstbyte_offset);
-
- map->l_tls_offset = GL(dl_tls_static_used) = offset;
-#elif TLS_DTV_AT_TP
- /* dl_tls_static_used includes the TCB at the beginning. */
- size_t offset = (ALIGN_UP(GL(dl_tls_static_used)
- - map->l_tls_firstbyte_offset,
- map->l_tls_align)
- + map->l_tls_firstbyte_offset);
- size_t used = offset + map->l_tls_blocksize;
-
- if (used > GL(dl_tls_static_size))
- goto fail;
-
- map->l_tls_offset = offset;
- map->l_tls_firstbyte_offset = GL(dl_tls_static_used);
- GL(dl_tls_static_used) = used;
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
-
- /* If the object is not yet relocated we cannot initialize the
- static TLS region. Delay it. */
- if (map->l_real->l_relocated)
- {
-#ifdef SHARED
- if (__builtin_expect (THREAD_DTV()[0].counter != GL(dl_tls_generation),
- 0))
- /* Update the slot information data for at least the generation of
- the DSO we are allocating data for. */
- (void) _dl_update_slotinfo (map->l_tls_modid);
-#endif
-
- GL(dl_init_static_tls) (map);
- }
- else
- map->l_need_tls_init = 1;
-
- return 0;
-}
-
-void
-internal_function __attribute_noinline__
-_dl_allocate_static_tls (struct link_map *map)
-{
- if (map->l_tls_offset == FORCED_DYNAMIC_TLS_OFFSET
- || _dl_try_allocate_static_tls (map))
- {
- _dl_signal_error (0, map->l_name, NULL, N_("\
-cannot allocate memory in static TLS block"));
- }
-}
-
-/* Initialize static TLS area and DTV for current (only) thread.
- libpthread implementations should provide their own hook
- to handle all threads. */
-void
-_dl_nothread_init_static_tls (struct link_map *map)
-{
-#if TLS_TCB_AT_TP
- void *dest = (char *) THREAD_SELF - map->l_tls_offset;
-#elif TLS_DTV_AT_TP
- void *dest = (char *) THREAD_SELF + map->l_tls_offset + TLS_PRE_TCB_SIZE;
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
-
- /* Initialize the memory. */
- memset (__mempcpy (dest, map->l_tls_initimage, map->l_tls_initimage_size),
- '\0', map->l_tls_blocksize - map->l_tls_initimage_size);
-}
-
-
-void
-_dl_relocate_object (struct link_map *l, struct r_scope_elem *scope[],
- int reloc_mode, int consider_profiling)
-{
- struct textrels
- {
- caddr_t start;
- size_t len;
- int prot;
- struct textrels *next;
- } *textrels = NULL;
- /* Initialize it to make the compiler happy. */
- const char *errstring = NULL;
- int lazy = reloc_mode & RTLD_LAZY;
- int skip_ifunc = reloc_mode & __RTLD_NOIFUNC;
-
-#ifdef SHARED
- /* If we are auditing, install the same handlers we need for profiling. */
- if ((reloc_mode & __RTLD_AUDIT) == 0)
- consider_profiling |= GLRO(dl_audit) != NULL;
-#elif defined PROF
- /* Never use dynamic linker profiling for gprof profiling code. */
-# define consider_profiling 0
-#endif
-
- if (l->l_relocated)
- return;
-
- /* If DT_BIND_NOW is set relocate all references in this object. We
- do not do this if we are profiling, of course. */
- // XXX Correct for auditing?
- if (!consider_profiling
- && __builtin_expect (l->l_info[DT_BIND_NOW] != NULL, 0))
- lazy = 0;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_RELOC))
- _dl_debug_printf ("\nrelocation processing: %s%s\n",
- DSO_FILENAME (l->l_name), lazy ? " (lazy)" : "");
-
- /* DT_TEXTREL is now in level 2 and might phase out at some time.
- But we rewrite the DT_FLAGS entry to a DT_TEXTREL entry to make
- testing easier and therefore it will be available at all time. */
- if (__glibc_unlikely (l->l_info[DT_TEXTREL] != NULL))
- {
- /* Bletch. We must make read-only segments writable
- long enough to relocate them. */
- const ElfW(Phdr) *ph;
- for (ph = l->l_phdr; ph < &l->l_phdr[l->l_phnum]; ++ph)
- if (ph->p_type == PT_LOAD && (ph->p_flags & PF_W) == 0)
- {
- struct textrels *newp;
-
- newp = (struct textrels *) alloca (sizeof (*newp));
- newp->len = ALIGN_UP (ph->p_vaddr + ph->p_memsz, GLRO(dl_pagesize))
- - ALIGN_DOWN (ph->p_vaddr, GLRO(dl_pagesize));
- newp->start = PTR_ALIGN_DOWN (ph->p_vaddr, GLRO(dl_pagesize))
- + (caddr_t) l->l_addr;
-
- if (__mprotect (newp->start, newp->len, PROT_READ|PROT_WRITE) < 0)
- {
- errstring = N_("cannot make segment writable for relocation");
- call_error:
- _dl_signal_error (errno, l->l_name, NULL, errstring);
- }
-
-#if (PF_R | PF_W | PF_X) == 7 && (PROT_READ | PROT_WRITE | PROT_EXEC) == 7
- newp->prot = (PF_TO_PROT
- >> ((ph->p_flags & (PF_R | PF_W | PF_X)) * 4)) & 0xf;
-#else
- newp->prot = 0;
- if (ph->p_flags & PF_R)
- newp->prot |= PROT_READ;
- if (ph->p_flags & PF_W)
- newp->prot |= PROT_WRITE;
- if (ph->p_flags & PF_X)
- newp->prot |= PROT_EXEC;
-#endif
- newp->next = textrels;
- textrels = newp;
- }
- }
-
- {
- /* Do the actual relocation of the object's GOT and other data. */
-
- /* String table object symbols. */
- const char *strtab = (const void *) D_PTR (l, l_info[DT_STRTAB]);
-
- /* This macro is used as a callback from the ELF_DYNAMIC_RELOCATE code. */
-#define RESOLVE_MAP(ref, version, r_type) \
- ((ELFW(ST_BIND) ((*ref)->st_info) != STB_LOCAL \
- && __glibc_likely (!dl_symbol_visibility_binds_local_p (*ref))) \
- ? ((__builtin_expect ((*ref) == l->l_lookup_cache.sym, 0) \
- && elf_machine_type_class (r_type) == l->l_lookup_cache.type_class) \
- ? (bump_num_cache_relocations (), \
- (*ref) = l->l_lookup_cache.ret, \
- l->l_lookup_cache.value) \
- : ({ lookup_t _lr; \
- int _tc = elf_machine_type_class (r_type); \
- l->l_lookup_cache.type_class = _tc; \
- l->l_lookup_cache.sym = (*ref); \
- const struct r_found_version *v = NULL; \
- if ((version) != NULL && (version)->hash != 0) \
- v = (version); \
- _lr = _dl_lookup_symbol_x (strtab + (*ref)->st_name, l, (ref), \
- scope, v, _tc, \
- DL_LOOKUP_ADD_DEPENDENCY, NULL); \
- l->l_lookup_cache.ret = (*ref); \
- l->l_lookup_cache.value = _lr; })) \
- : l)
-
-#include "dynamic-link.h"
-
- ELF_DYNAMIC_RELOCATE (l, lazy, consider_profiling, skip_ifunc);
-
-#ifndef PROF
- if (__glibc_unlikely (consider_profiling)
- && l->l_info[DT_PLTRELSZ] != NULL)
- {
- /* Allocate the array which will contain the already found
- relocations. If the shared object lacks a PLT (for example
- if it only contains lead function) the l_info[DT_PLTRELSZ]
- will be NULL. */
- size_t sizeofrel = l->l_info[DT_PLTREL]->d_un.d_val == DT_RELA
- ? sizeof (ElfW(Rela))
- : sizeof (ElfW(Rel));
- size_t relcount = l->l_info[DT_PLTRELSZ]->d_un.d_val / sizeofrel;
- l->l_reloc_result = calloc (sizeof (l->l_reloc_result[0]), relcount);
-
- if (l->l_reloc_result == NULL)
- {
- errstring = N_("\
-%s: out of memory to store relocation results for %s\n");
- _dl_fatal_printf (errstring, RTLD_PROGNAME, l->l_name);
- }
- }
-#endif
- }
-
- /* Mark the object so we know this work has been done. */
- l->l_relocated = 1;
-
- /* Undo the segment protection changes. */
- while (__builtin_expect (textrels != NULL, 0))
- {
- if (__mprotect (textrels->start, textrels->len, textrels->prot) < 0)
- {
- errstring = N_("cannot restore segment prot after reloc");
- goto call_error;
- }
-
-#ifdef CLEAR_CACHE
- CLEAR_CACHE (textrels->start, textrels->start + textrels->len);
-#endif
-
- textrels = textrels->next;
- }
-
- /* In case we can protect the data now that the relocations are
- done, do it. */
- if (l->l_relro_size != 0)
- _dl_protect_relro (l);
-}
-
-
-void internal_function
-_dl_protect_relro (struct link_map *l)
-{
- ElfW(Addr) start = ALIGN_DOWN((l->l_addr
- + l->l_relro_addr),
- GLRO(dl_pagesize));
- ElfW(Addr) end = ALIGN_DOWN((l->l_addr
- + l->l_relro_addr
- + l->l_relro_size),
- GLRO(dl_pagesize));
- if (start != end
- && __mprotect ((void *) start, end - start, PROT_READ) < 0)
- {
- static const char errstring[] = N_("\
-cannot apply additional memory protection after relocation");
- _dl_signal_error (errno, l->l_name, NULL, errstring);
- }
-}
-
-void
-internal_function __attribute_noinline__
-_dl_reloc_bad_type (struct link_map *map, unsigned int type, int plt)
-{
-#define DIGIT(b) _itoa_lower_digits[(b) & 0xf];
-
- /* XXX We cannot translate these messages. */
- static const char msg[2][32
-#if __ELF_NATIVE_CLASS == 64
- + 6
-#endif
- ] = { "unexpected reloc type 0x",
- "unexpected PLT reloc type 0x" };
- char msgbuf[sizeof (msg[0])];
- char *cp;
-
- cp = __stpcpy (msgbuf, msg[plt]);
-#if __ELF_NATIVE_CLASS == 64
- if (__builtin_expect(type > 0xff, 0))
- {
- *cp++ = DIGIT (type >> 28);
- *cp++ = DIGIT (type >> 24);
- *cp++ = DIGIT (type >> 20);
- *cp++ = DIGIT (type >> 16);
- *cp++ = DIGIT (type >> 12);
- *cp++ = DIGIT (type >> 8);
- }
-#endif
- *cp++ = DIGIT (type >> 4);
- *cp++ = DIGIT (type);
- *cp = '\0';
-
- _dl_signal_error (0, map->l_name, NULL, msgbuf);
-}
diff --git a/elf/dl-runtime.c b/elf/dl-runtime.c
deleted file mode 100644
index 7d1d240403..0000000000
--- a/elf/dl-runtime.c
+++ /dev/null
@@ -1,480 +0,0 @@
-/* On-demand PLT fixup for shared objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#define IN_DL_RUNTIME 1 /* This can be tested in dl-machine.h. */
-
-#include <alloca.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <sys/param.h>
-#include <ldsodefs.h>
-#include <sysdep-cancel.h>
-#include "dynamic-link.h"
-#include <tls.h>
-#include <dl-irel.h>
-
-
-#if (!ELF_MACHINE_NO_RELA && !defined ELF_MACHINE_PLT_REL) \
- || ELF_MACHINE_NO_REL
-# define PLTREL ElfW(Rela)
-#else
-# define PLTREL ElfW(Rel)
-#endif
-
-/* The fixup functions might have need special attributes. If none
- are provided define the macro as empty. */
-#ifndef ARCH_FIXUP_ATTRIBUTE
-# define ARCH_FIXUP_ATTRIBUTE
-#endif
-
-#ifndef reloc_offset
-# define reloc_offset reloc_arg
-# define reloc_index reloc_arg / sizeof (PLTREL)
-#endif
-
-
-
-/* This function is called through a special trampoline from the PLT the
- first time each PLT entry is called. We must perform the relocation
- specified in the PLT of the given shared object, and return the resolved
- function address to the trampoline, which will restart the original call
- to that address. Future calls will bounce directly from the PLT to the
- function. */
-
-DL_FIXUP_VALUE_TYPE
-attribute_hidden __attribute ((noinline)) ARCH_FIXUP_ATTRIBUTE
-_dl_fixup (
-# ifdef ELF_MACHINE_RUNTIME_FIXUP_ARGS
- ELF_MACHINE_RUNTIME_FIXUP_ARGS,
-# endif
- struct link_map *l, ElfW(Word) reloc_arg)
-{
- const ElfW(Sym) *const symtab
- = (const void *) D_PTR (l, l_info[DT_SYMTAB]);
- const char *strtab = (const void *) D_PTR (l, l_info[DT_STRTAB]);
-
- const PLTREL *const reloc
- = (const void *) (D_PTR (l, l_info[DT_JMPREL]) + reloc_offset);
- const ElfW(Sym) *sym = &symtab[ELFW(R_SYM) (reloc->r_info)];
- void *const rel_addr = (void *)(l->l_addr + reloc->r_offset);
- lookup_t result;
- DL_FIXUP_VALUE_TYPE value;
-
- /* Sanity check that we're really looking at a PLT relocation. */
- assert (ELFW(R_TYPE)(reloc->r_info) == ELF_MACHINE_JMP_SLOT);
-
- /* Look up the target symbol. If the normal lookup rules are not
- used don't look in the global scope. */
- if (__builtin_expect (ELFW(ST_VISIBILITY) (sym->st_other), 0) == 0)
- {
- const struct r_found_version *version = NULL;
-
- if (l->l_info[VERSYMIDX (DT_VERSYM)] != NULL)
- {
- const ElfW(Half) *vernum =
- (const void *) D_PTR (l, l_info[VERSYMIDX (DT_VERSYM)]);
- ElfW(Half) ndx = vernum[ELFW(R_SYM) (reloc->r_info)] & 0x7fff;
- version = &l->l_versions[ndx];
- if (version->hash == 0)
- version = NULL;
- }
-
- /* We need to keep the scope around so do some locking. This is
- not necessary for objects which cannot be unloaded or when
- we are not using any threads (yet). */
- int flags = DL_LOOKUP_ADD_DEPENDENCY;
- if (!RTLD_SINGLE_THREAD_P)
- {
- THREAD_GSCOPE_SET_FLAG ();
- flags |= DL_LOOKUP_GSCOPE_LOCK;
- }
-
-#ifdef RTLD_ENABLE_FOREIGN_CALL
- RTLD_ENABLE_FOREIGN_CALL;
-#endif
-
- result = _dl_lookup_symbol_x (strtab + sym->st_name, l, &sym, l->l_scope,
- version, ELF_RTYPE_CLASS_PLT, flags, NULL);
-
- /* We are done with the global scope. */
- if (!RTLD_SINGLE_THREAD_P)
- THREAD_GSCOPE_RESET_FLAG ();
-
-#ifdef RTLD_FINALIZE_FOREIGN_CALL
- RTLD_FINALIZE_FOREIGN_CALL;
-#endif
-
- /* Currently result contains the base load address (or link map)
- of the object that defines sym. Now add in the symbol
- offset. */
- value = DL_FIXUP_MAKE_VALUE (result,
- sym ? (LOOKUP_VALUE_ADDRESS (result)
- + sym->st_value) : 0);
- }
- else
- {
- /* We already found the symbol. The module (and therefore its load
- address) is also known. */
- value = DL_FIXUP_MAKE_VALUE (l, l->l_addr + sym->st_value);
- result = l;
- }
-
- /* And now perhaps the relocation addend. */
- value = elf_machine_plt_value (l, reloc, value);
-
- if (sym != NULL
- && __builtin_expect (ELFW(ST_TYPE) (sym->st_info) == STT_GNU_IFUNC, 0))
- value = elf_ifunc_invoke (DL_FIXUP_VALUE_ADDR (value));
-
- /* Finally, fix up the plt itself. */
- if (__glibc_unlikely (GLRO(dl_bind_not)))
- return value;
-
- return elf_machine_fixup_plt (l, result, reloc, rel_addr, value);
-}
-
-#ifndef PROF
-DL_FIXUP_VALUE_TYPE
-__attribute ((noinline)) ARCH_FIXUP_ATTRIBUTE
-_dl_profile_fixup (
-#ifdef ELF_MACHINE_RUNTIME_FIXUP_ARGS
- ELF_MACHINE_RUNTIME_FIXUP_ARGS,
-#endif
- struct link_map *l, ElfW(Word) reloc_arg,
- ElfW(Addr) retaddr, void *regs, long int *framesizep)
-{
- void (*mcount_fct) (ElfW(Addr), ElfW(Addr)) = _dl_mcount;
-
- if (l->l_reloc_result == NULL)
- {
- /* BZ #14843: ELF_DYNAMIC_RELOCATE is called before l_reloc_result
- is allocated. We will get here if ELF_DYNAMIC_RELOCATE calls a
- resolver function to resolve an IRELATIVE relocation and that
- resolver calls a function that is not yet resolved (lazy). For
- example, the resolver in x86-64 libm.so calls __get_cpu_features
- defined in libc.so. Skip audit and resolve the external function
- in this case. */
- *framesizep = -1;
- return _dl_fixup (
-# ifdef ELF_MACHINE_RUNTIME_FIXUP_ARGS
-# ifndef ELF_MACHINE_RUNTIME_FIXUP_PARAMS
-# error Please define ELF_MACHINE_RUNTIME_FIXUP_PARAMS.
-# endif
- ELF_MACHINE_RUNTIME_FIXUP_PARAMS,
-# endif
- l, reloc_arg);
- }
-
- /* This is the address in the array where we store the result of previous
- relocations. */
- struct reloc_result *reloc_result = &l->l_reloc_result[reloc_index];
- DL_FIXUP_VALUE_TYPE *resultp = &reloc_result->addr;
-
- DL_FIXUP_VALUE_TYPE value = *resultp;
- if (DL_FIXUP_VALUE_CODE_ADDR (value) == 0)
- {
- /* This is the first time we have to relocate this object. */
- const ElfW(Sym) *const symtab
- = (const void *) D_PTR (l, l_info[DT_SYMTAB]);
- const char *strtab = (const char *) D_PTR (l, l_info[DT_STRTAB]);
-
- const PLTREL *const reloc
- = (const void *) (D_PTR (l, l_info[DT_JMPREL]) + reloc_offset);
- const ElfW(Sym) *refsym = &symtab[ELFW(R_SYM) (reloc->r_info)];
- const ElfW(Sym) *defsym = refsym;
- lookup_t result;
-
- /* Sanity check that we're really looking at a PLT relocation. */
- assert (ELFW(R_TYPE)(reloc->r_info) == ELF_MACHINE_JMP_SLOT);
-
- /* Look up the target symbol. If the symbol is marked STV_PROTECTED
- don't look in the global scope. */
- if (__builtin_expect (ELFW(ST_VISIBILITY) (refsym->st_other), 0) == 0)
- {
- const struct r_found_version *version = NULL;
-
- if (l->l_info[VERSYMIDX (DT_VERSYM)] != NULL)
- {
- const ElfW(Half) *vernum =
- (const void *) D_PTR (l, l_info[VERSYMIDX (DT_VERSYM)]);
- ElfW(Half) ndx = vernum[ELFW(R_SYM) (reloc->r_info)] & 0x7fff;
- version = &l->l_versions[ndx];
- if (version->hash == 0)
- version = NULL;
- }
-
- /* We need to keep the scope around so do some locking. This is
- not necessary for objects which cannot be unloaded or when
- we are not using any threads (yet). */
- int flags = DL_LOOKUP_ADD_DEPENDENCY;
- if (!RTLD_SINGLE_THREAD_P)
- {
- THREAD_GSCOPE_SET_FLAG ();
- flags |= DL_LOOKUP_GSCOPE_LOCK;
- }
-
- result = _dl_lookup_symbol_x (strtab + refsym->st_name, l,
- &defsym, l->l_scope, version,
- ELF_RTYPE_CLASS_PLT, flags, NULL);
-
- /* We are done with the global scope. */
- if (!RTLD_SINGLE_THREAD_P)
- THREAD_GSCOPE_RESET_FLAG ();
-
- /* Currently result contains the base load address (or link map)
- of the object that defines sym. Now add in the symbol
- offset. */
- value = DL_FIXUP_MAKE_VALUE (result,
- defsym != NULL
- ? LOOKUP_VALUE_ADDRESS (result)
- + defsym->st_value : 0);
-
- if (defsym != NULL
- && __builtin_expect (ELFW(ST_TYPE) (defsym->st_info)
- == STT_GNU_IFUNC, 0))
- value = elf_ifunc_invoke (DL_FIXUP_VALUE_ADDR (value));
- }
- else
- {
- /* We already found the symbol. The module (and therefore its load
- address) is also known. */
- value = DL_FIXUP_MAKE_VALUE (l, l->l_addr + refsym->st_value);
-
- if (__builtin_expect (ELFW(ST_TYPE) (refsym->st_info)
- == STT_GNU_IFUNC, 0))
- value = elf_ifunc_invoke (DL_FIXUP_VALUE_ADDR (value));
-
- result = l;
- }
- /* And now perhaps the relocation addend. */
- value = elf_machine_plt_value (l, reloc, value);
-
-#ifdef SHARED
- /* Auditing checkpoint: we have a new binding. Provide the
- auditing libraries the possibility to change the value and
- tell us whether further auditing is wanted. */
- if (defsym != NULL && GLRO(dl_naudit) > 0)
- {
- reloc_result->bound = result;
- /* Compute index of the symbol entry in the symbol table of
- the DSO with the definition. */
- reloc_result->boundndx = (defsym
- - (ElfW(Sym) *) D_PTR (result,
- l_info[DT_SYMTAB]));
-
- /* Determine whether any of the two participating DSOs is
- interested in auditing. */
- if ((l->l_audit_any_plt | result->l_audit_any_plt) != 0)
- {
- unsigned int flags = 0;
- struct audit_ifaces *afct = GLRO(dl_audit);
- /* Synthesize a symbol record where the st_value field is
- the result. */
- ElfW(Sym) sym = *defsym;
- sym.st_value = DL_FIXUP_VALUE_ADDR (value);
-
- /* Keep track whether there is any interest in tracing
- the call in the lower two bits. */
- assert (DL_NNS * 2 <= sizeof (reloc_result->flags) * 8);
- assert ((LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT) == 3);
- reloc_result->enterexit = LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT;
-
- const char *strtab2 = (const void *) D_PTR (result,
- l_info[DT_STRTAB]);
-
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- /* XXX Check whether both DSOs must request action or
- only one */
- if ((l->l_audit[cnt].bindflags & LA_FLG_BINDFROM) != 0
- && (result->l_audit[cnt].bindflags & LA_FLG_BINDTO) != 0)
- {
- if (afct->symbind != NULL)
- {
- uintptr_t new_value
- = afct->symbind (&sym, reloc_result->boundndx,
- &l->l_audit[cnt].cookie,
- &result->l_audit[cnt].cookie,
- &flags,
- strtab2 + defsym->st_name);
- if (new_value != (uintptr_t) sym.st_value)
- {
- flags |= LA_SYMB_ALTVALUE;
- sym.st_value = new_value;
- }
- }
-
- /* Remember the results for every audit library and
- store a summary in the first two bits. */
- reloc_result->enterexit
- &= flags & (LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT);
- reloc_result->enterexit
- |= ((flags & (LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT))
- << ((cnt + 1) * 2));
- }
- else
- /* If the bind flags say this auditor is not interested,
- set the bits manually. */
- reloc_result->enterexit
- |= ((LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT)
- << ((cnt + 1) * 2));
-
- afct = afct->next;
- }
-
- reloc_result->flags = flags;
- value = DL_FIXUP_ADDR_VALUE (sym.st_value);
- }
- else
- /* Set all bits since this symbol binding is not interesting. */
- reloc_result->enterexit = (1u << DL_NNS) - 1;
- }
-#endif
-
- /* Store the result for later runs. */
- if (__glibc_likely (! GLRO(dl_bind_not)))
- *resultp = value;
- }
-
- /* By default we do not call the pltexit function. */
- long int framesize = -1;
-
-#ifdef SHARED
- /* Auditing checkpoint: report the PLT entering and allow the
- auditors to change the value. */
- if (DL_FIXUP_VALUE_CODE_ADDR (value) != 0 && GLRO(dl_naudit) > 0
- /* Don't do anything if no auditor wants to intercept this call. */
- && (reloc_result->enterexit & LA_SYMB_NOPLTENTER) == 0)
- {
- ElfW(Sym) *defsym = ((ElfW(Sym) *) D_PTR (reloc_result->bound,
- l_info[DT_SYMTAB])
- + reloc_result->boundndx);
-
- /* Set up the sym parameter. */
- ElfW(Sym) sym = *defsym;
- sym.st_value = DL_FIXUP_VALUE_ADDR (value);
-
- /* Get the symbol name. */
- const char *strtab = (const void *) D_PTR (reloc_result->bound,
- l_info[DT_STRTAB]);
- const char *symname = strtab + sym.st_name;
-
- /* Keep track of overwritten addresses. */
- unsigned int flags = reloc_result->flags;
-
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->ARCH_LA_PLTENTER != NULL
- && (reloc_result->enterexit
- & (LA_SYMB_NOPLTENTER << (2 * (cnt + 1)))) == 0)
- {
- long int new_framesize = -1;
- uintptr_t new_value
- = afct->ARCH_LA_PLTENTER (&sym, reloc_result->boundndx,
- &l->l_audit[cnt].cookie,
- &reloc_result->bound->l_audit[cnt].cookie,
- regs, &flags, symname,
- &new_framesize);
- if (new_value != (uintptr_t) sym.st_value)
- {
- flags |= LA_SYMB_ALTVALUE;
- sym.st_value = new_value;
- }
-
- /* Remember the results for every audit library and
- store a summary in the first two bits. */
- reloc_result->enterexit
- |= ((flags & (LA_SYMB_NOPLTENTER | LA_SYMB_NOPLTEXIT))
- << (2 * (cnt + 1)));
-
- if ((reloc_result->enterexit & (LA_SYMB_NOPLTEXIT
- << (2 * (cnt + 1))))
- == 0 && new_framesize != -1 && framesize != -2)
- {
- /* If this is the first call providing information,
- use it. */
- if (framesize == -1)
- framesize = new_framesize;
- /* If two pltenter calls provide conflicting information,
- use the larger value. */
- else if (new_framesize != framesize)
- framesize = MAX (new_framesize, framesize);
- }
- }
-
- afct = afct->next;
- }
-
- value = DL_FIXUP_ADDR_VALUE (sym.st_value);
- }
-#endif
-
- /* Store the frame size information. */
- *framesizep = framesize;
-
- (*mcount_fct) (retaddr, DL_FIXUP_VALUE_CODE_ADDR (value));
-
- return value;
-}
-
-#endif /* PROF */
-
-
-#include <stdio.h>
-void
-ARCH_FIXUP_ATTRIBUTE
-_dl_call_pltexit (struct link_map *l, ElfW(Word) reloc_arg,
- const void *inregs, void *outregs)
-{
-#ifdef SHARED
- /* This is the address in the array where we store the result of previous
- relocations. */
- // XXX Maybe the bound information must be stored on the stack since
- // XXX with bind_not a new value could have been stored in the meantime.
- struct reloc_result *reloc_result = &l->l_reloc_result[reloc_index];
- ElfW(Sym) *defsym = ((ElfW(Sym) *) D_PTR (reloc_result->bound,
- l_info[DT_SYMTAB])
- + reloc_result->boundndx);
-
- /* Set up the sym parameter. */
- ElfW(Sym) sym = *defsym;
- sym.st_value = DL_FIXUP_VALUE_ADDR (reloc_result->addr);
-
- /* Get the symbol name. */
- const char *strtab = (const void *) D_PTR (reloc_result->bound,
- l_info[DT_STRTAB]);
- const char *symname = strtab + sym.st_name;
-
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->ARCH_LA_PLTEXIT != NULL
- && (reloc_result->enterexit
- & (LA_SYMB_NOPLTEXIT >> (2 * cnt))) == 0)
- {
- afct->ARCH_LA_PLTEXIT (&sym, reloc_result->boundndx,
- &l->l_audit[cnt].cookie,
- &reloc_result->bound->l_audit[cnt].cookie,
- inregs, outregs, symname);
- }
-
- afct = afct->next;
- }
-#endif
-}
diff --git a/elf/dl-sbrk.c b/elf/dl-sbrk.c
deleted file mode 100644
index 4713a92694..0000000000
--- a/elf/dl-sbrk.c
+++ /dev/null
@@ -1,5 +0,0 @@
-/* We can use the normal code but we also know the __curbrk is not exported
- from ld.so. */
-extern void *__curbrk attribute_hidden;
-
-#include <sbrk.c>
diff --git a/elf/dl-scope.c b/elf/dl-scope.c
deleted file mode 100644
index bb924afa8f..0000000000
--- a/elf/dl-scope.c
+++ /dev/null
@@ -1,57 +0,0 @@
-/* Memory handling for the scope data structures.
- Copyright (C) 2009-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdlib.h>
-#include <ldsodefs.h>
-#include <sysdep-cancel.h>
-
-
-int
-_dl_scope_free (void *old)
-{
- struct dl_scope_free_list *fsl;
-#define DL_SCOPE_FREE_LIST_SIZE (sizeof (fsl->list) / sizeof (fsl->list[0]))
-
- if (RTLD_SINGLE_THREAD_P)
- free (old);
- else if ((fsl = GL(dl_scope_free_list)) == NULL)
- {
- GL(dl_scope_free_list) = fsl = malloc (sizeof (*fsl));
- if (fsl == NULL)
- {
- THREAD_GSCOPE_WAIT ();
- free (old);
- return 1;
- }
- else
- {
- fsl->list[0] = old;
- fsl->count = 1;
- }
- }
- else if (fsl->count < DL_SCOPE_FREE_LIST_SIZE)
- fsl->list[fsl->count++] = old;
- else
- {
- THREAD_GSCOPE_WAIT ();
- while (fsl->count > 0)
- free (fsl->list[--fsl->count]);
- return 1;
- }
- return 0;
-}
diff --git a/elf/dl-support.c b/elf/dl-support.c
deleted file mode 100644
index c22be854f4..0000000000
--- a/elf/dl-support.c
+++ /dev/null
@@ -1,389 +0,0 @@
-/* Support for dynamic linking code in static libc.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file defines some things that for the dynamic linker are defined in
- rtld.c and dl-sysdep.c in ways appropriate to bootstrap dynamic linking. */
-
-#include <errno.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <sys/param.h>
-#include <stdint.h>
-#include <ldsodefs.h>
-#include <dl-machine.h>
-#include <libc-lock.h>
-#include <dl-cache.h>
-#include <dl-librecon.h>
-#include <dl-procinfo.h>
-#include <unsecvars.h>
-#include <hp-timing.h>
-#include <stackinfo.h>
-
-extern char *__progname;
-char **_dl_argv = &__progname; /* This is checked for some error messages. */
-
-/* Name of the architecture. */
-const char *_dl_platform;
-size_t _dl_platformlen;
-
-int _dl_debug_mask;
-int _dl_lazy;
-ElfW(Addr) _dl_use_load_bias = -2;
-int _dl_dynamic_weak;
-
-/* If nonzero print warnings about problematic situations. */
-int _dl_verbose;
-
-/* We never do profiling. */
-const char *_dl_profile;
-const char *_dl_profile_output;
-
-/* Names of shared object for which the RUNPATHs and RPATHs should be
- ignored. */
-const char *_dl_inhibit_rpath;
-
-/* The map for the object we will profile. */
-struct link_map *_dl_profile_map;
-
-/* This is the address of the last stack address ever used. */
-void *__libc_stack_end;
-
-/* Path where the binary is found. */
-const char *_dl_origin_path;
-
-/* Nonzero if runtime lookup should not update the .got/.plt. */
-int _dl_bind_not;
-
-/* A dummy link map for the executable, used by dlopen to access the global
- scope. We don't export any symbols ourselves, so this can be minimal. */
-static struct link_map _dl_main_map =
- {
- .l_name = (char *) "",
- .l_real = &_dl_main_map,
- .l_ns = LM_ID_BASE,
- .l_libname = &(struct libname_list) { .name = "", .dont_free = 1 },
- .l_searchlist =
- {
- .r_list = &(struct link_map *) { &_dl_main_map },
- .r_nlist = 1,
- },
- .l_symbolic_searchlist = { .r_list = &(struct link_map *) { NULL } },
- .l_type = lt_executable,
- .l_scope_mem = { &_dl_main_map.l_searchlist },
- .l_scope_max = (sizeof (_dl_main_map.l_scope_mem)
- / sizeof (_dl_main_map.l_scope_mem[0])),
- .l_scope = _dl_main_map.l_scope_mem,
- .l_local_scope = { &_dl_main_map.l_searchlist },
- .l_used = 1,
- .l_tls_offset = NO_TLS_OFFSET,
- .l_serial = 1,
- };
-
-/* Namespace information. */
-struct link_namespaces _dl_ns[DL_NNS] =
- {
- [LM_ID_BASE] =
- {
- ._ns_loaded = &_dl_main_map,
- ._ns_nloaded = 1,
- ._ns_main_searchlist = &_dl_main_map.l_searchlist,
- }
- };
-size_t _dl_nns = 1;
-
-/* Incremented whenever something may have been added to dl_loaded. */
-unsigned long long _dl_load_adds = 1;
-
-/* Fake scope of the main application. */
-struct r_scope_elem _dl_initial_searchlist =
- {
- .r_list = &(struct link_map *) { &_dl_main_map },
- .r_nlist = 1,
- };
-
-#ifndef HAVE_INLINED_SYSCALLS
-/* Nonzero during startup. */
-int _dl_starting_up = 1;
-#endif
-
-/* Random data provided by the kernel. */
-void *_dl_random;
-
-/* Get architecture specific initializer. */
-#include <dl-procinfo.c>
-
-/* Initial value of the CPU clock. */
-#ifndef HP_TIMING_NONAVAIL
-hp_timing_t _dl_cpuclock_offset;
-#endif
-
-void (*_dl_init_static_tls) (struct link_map *) = &_dl_nothread_init_static_tls;
-
-size_t _dl_pagesize = EXEC_PAGESIZE;
-
-int _dl_inhibit_cache;
-
-unsigned int _dl_osversion;
-
-/* All known directories in sorted order. */
-struct r_search_path_elem *_dl_all_dirs;
-
-/* All directories after startup. */
-struct r_search_path_elem *_dl_init_all_dirs;
-
-/* The object to be initialized first. */
-struct link_map *_dl_initfirst;
-
-/* Descriptor to write debug messages to. */
-int _dl_debug_fd = STDERR_FILENO;
-
-int _dl_correct_cache_id = _DL_CACHE_DEFAULT_ID;
-
-ElfW(auxv_t) *_dl_auxv;
-const ElfW(Phdr) *_dl_phdr;
-size_t _dl_phnum;
-uint64_t _dl_hwcap __attribute__ ((nocommon));
-uint64_t _dl_hwcap2 __attribute__ ((nocommon));
-
-/* The value of the FPU control word the kernel will preset in hardware. */
-fpu_control_t _dl_fpu_control = _FPU_DEFAULT;
-
-#if !HAVE_TUNABLES
-/* This is not initialized to HWCAP_IMPORTANT, matching the definition
- of _dl_important_hwcaps, below, where no hwcap strings are ever
- used. This mask is still used to mediate the lookups in the cache
- file. Since there is no way to set this nonzero (we don't grok the
- LD_HWCAP_MASK environment variable here), there is no real point in
- setting _dl_hwcap nonzero below, but we do anyway. */
-uint64_t _dl_hwcap_mask __attribute__ ((nocommon));
-#endif
-
-/* Prevailing state of the stack. Generally this includes PF_X, indicating it's
- * executable but this isn't true for all platforms. */
-ElfW(Word) _dl_stack_flags = DEFAULT_STACK_PERMS;
-
-/* If loading a shared object requires that we make the stack executable
- when it was not, we do it by calling this function.
- It returns an errno code or zero on success. */
-int (*_dl_make_stack_executable_hook) (void **) internal_function
- = _dl_make_stack_executable;
-
-
-/* Function in libpthread to wait for termination of lookups. */
-void (*_dl_wait_lookup_done) (void);
-
-struct dl_scope_free_list *_dl_scope_free_list;
-
-#ifdef NEED_DL_SYSINFO
-/* Needed for improved syscall handling on at least x86/Linux. */
-uintptr_t _dl_sysinfo = DL_SYSINFO_DEFAULT;
-#endif
-#ifdef NEED_DL_SYSINFO_DSO
-/* Address of the ELF headers in the vsyscall page. */
-const ElfW(Ehdr) *_dl_sysinfo_dso;
-
-struct link_map *_dl_sysinfo_map;
-
-# include "get-dynamic-info.h"
-#endif
-#include "setup-vdso.h"
-
-/* During the program run we must not modify the global data of
- loaded shared object simultanously in two threads. Therefore we
- protect `_dl_open' and `_dl_close' in dl-close.c.
-
- This must be a recursive lock since the initializer function of
- the loaded object might as well require a call to this function.
- At this time it is not anymore a problem to modify the tables. */
-__rtld_lock_define_initialized_recursive (, _dl_load_lock)
-/* This lock is used to keep __dl_iterate_phdr from inspecting the
- list of loaded objects while an object is added to or removed from
- that list. */
-__rtld_lock_define_initialized_recursive (, _dl_load_write_lock)
-
-
-#ifdef HAVE_AUX_VECTOR
-int _dl_clktck;
-
-void
-internal_function
-_dl_aux_init (ElfW(auxv_t) *av)
-{
- int seen = 0;
- uid_t uid = 0;
- gid_t gid = 0;
-
- _dl_auxv = av;
- for (; av->a_type != AT_NULL; ++av)
- switch (av->a_type)
- {
- case AT_PAGESZ:
- if (av->a_un.a_val != 0)
- GLRO(dl_pagesize) = av->a_un.a_val;
- break;
- case AT_CLKTCK:
- GLRO(dl_clktck) = av->a_un.a_val;
- break;
- case AT_PHDR:
- GL(dl_phdr) = (const void *) av->a_un.a_val;
- break;
- case AT_PHNUM:
- GL(dl_phnum) = av->a_un.a_val;
- break;
- case AT_PLATFORM:
- GLRO(dl_platform) = (void *) av->a_un.a_val;
- break;
- case AT_HWCAP:
- GLRO(dl_hwcap) = (unsigned long int) av->a_un.a_val;
- break;
- case AT_HWCAP2:
- GLRO(dl_hwcap2) = (unsigned long int) av->a_un.a_val;
- break;
- case AT_FPUCW:
- GLRO(dl_fpu_control) = av->a_un.a_val;
- break;
-#ifdef NEED_DL_SYSINFO
- case AT_SYSINFO:
- GL(dl_sysinfo) = av->a_un.a_val;
- break;
-#endif
-#ifdef NEED_DL_SYSINFO_DSO
- case AT_SYSINFO_EHDR:
- GL(dl_sysinfo_dso) = (void *) av->a_un.a_val;
- break;
-#endif
- case AT_UID:
- uid ^= av->a_un.a_val;
- seen |= 1;
- break;
- case AT_EUID:
- uid ^= av->a_un.a_val;
- seen |= 2;
- break;
- case AT_GID:
- gid ^= av->a_un.a_val;
- seen |= 4;
- break;
- case AT_EGID:
- gid ^= av->a_un.a_val;
- seen |= 8;
- break;
- case AT_SECURE:
- seen = -1;
- __libc_enable_secure = av->a_un.a_val;
- __libc_enable_secure_decided = 1;
- break;
- case AT_RANDOM:
- _dl_random = (void *) av->a_un.a_val;
- break;
-# ifdef DL_PLATFORM_AUXV
- DL_PLATFORM_AUXV
-# endif
- }
- if (seen == 0xf)
- {
- __libc_enable_secure = uid != 0 || gid != 0;
- __libc_enable_secure_decided = 1;
- }
-}
-#endif
-
-
-void
-internal_function
-_dl_non_dynamic_init (void)
-{
- _dl_main_map.l_origin = _dl_get_origin ();
- _dl_main_map.l_phdr = GL(dl_phdr);
- _dl_main_map.l_phnum = GL(dl_phnum);
-
- if (HP_SMALL_TIMING_AVAIL)
- HP_TIMING_NOW (_dl_cpuclock_offset);
-
- _dl_verbose = *(getenv ("LD_WARN") ?: "") == '\0' ? 0 : 1;
-
- /* Set up the data structures for the system-supplied DSO early,
- so they can influence _dl_init_paths. */
- setup_vdso (NULL, NULL);
-
- /* Initialize the data structures for the search paths for shared
- objects. */
- _dl_init_paths (getenv ("LD_LIBRARY_PATH"));
-
- /* Remember the last search directory added at startup. */
- _dl_init_all_dirs = GL(dl_all_dirs);
-
- _dl_lazy = *(getenv ("LD_BIND_NOW") ?: "") == '\0';
-
- _dl_bind_not = *(getenv ("LD_BIND_NOT") ?: "") != '\0';
-
- _dl_dynamic_weak = *(getenv ("LD_DYNAMIC_WEAK") ?: "") == '\0';
-
- _dl_profile_output = getenv ("LD_PROFILE_OUTPUT");
- if (_dl_profile_output == NULL || _dl_profile_output[0] == '\0')
- _dl_profile_output
- = &"/var/tmp\0/var/profile"[__libc_enable_secure ? 9 : 0];
-
- if (__libc_enable_secure)
- {
- static const char unsecure_envvars[] =
- UNSECURE_ENVVARS
-#ifdef EXTRA_UNSECURE_ENVVARS
- EXTRA_UNSECURE_ENVVARS
-#endif
- ;
- const char *cp = unsecure_envvars;
-
- while (cp < unsecure_envvars + sizeof (unsecure_envvars))
- {
- __unsetenv (cp);
- cp = (const char *) __rawmemchr (cp, '\0') + 1;
- }
-
-#if !HAVE_TUNABLES
- if (__access ("/etc/suid-debug", F_OK) != 0)
- __unsetenv ("MALLOC_CHECK_");
-#endif
- }
-
-#ifdef DL_PLATFORM_INIT
- DL_PLATFORM_INIT;
-#endif
-
-#ifdef DL_OSVERSION_INIT
- DL_OSVERSION_INIT;
-#endif
-
- /* Now determine the length of the platform string. */
- if (_dl_platform != NULL)
- _dl_platformlen = strlen (_dl_platform);
-
- /* Scan for a program header telling us the stack is nonexecutable. */
- if (_dl_phdr != NULL)
- for (uint_fast16_t i = 0; i < _dl_phnum; ++i)
- if (_dl_phdr[i].p_type == PT_GNU_STACK)
- {
- _dl_stack_flags = _dl_phdr[i].p_flags;
- break;
- }
-}
-
-#ifdef DL_SYSINFO_IMPLEMENTATION
-DL_SYSINFO_IMPLEMENTATION
-#endif
diff --git a/elf/dl-sym.c b/elf/dl-sym.c
deleted file mode 100644
index 7cd6e97643..0000000000
--- a/elf/dl-sym.c
+++ /dev/null
@@ -1,274 +0,0 @@
-/* Look up a symbol in a shared object loaded by `dlopen'.
- Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <stddef.h>
-#include <setjmp.h>
-#include <stdlib.h>
-#include <libintl.h>
-
-#include <dlfcn.h>
-#include <ldsodefs.h>
-#include <dl-hash.h>
-#include <sysdep-cancel.h>
-#include <dl-tls.h>
-#include <dl-irel.h>
-
-
-#ifdef SHARED
-/* Systems which do not have tls_index also probably have to define
- DONT_USE_TLS_INDEX. */
-
-# ifndef __TLS_GET_ADDR
-# define __TLS_GET_ADDR __tls_get_addr
-# endif
-
-/* Return the symbol address given the map of the module it is in and
- the symbol record. This is used in dl-sym.c. */
-static void *
-internal_function
-_dl_tls_symaddr (struct link_map *map, const ElfW(Sym) *ref)
-{
-# ifndef DONT_USE_TLS_INDEX
- tls_index tmp =
- {
- .ti_module = map->l_tls_modid,
- .ti_offset = ref->st_value
- };
-
- return __TLS_GET_ADDR (&tmp);
-# else
- return __TLS_GET_ADDR (map->l_tls_modid, ref->st_value);
-# endif
-}
-#endif
-
-
-struct call_dl_lookup_args
-{
- /* Arguments to do_dlsym. */
- struct link_map *map;
- const char *name;
- struct r_found_version *vers;
- int flags;
-
- /* Return values of do_dlsym. */
- lookup_t loadbase;
- const ElfW(Sym) **refp;
-};
-
-static void
-call_dl_lookup (void *ptr)
-{
- struct call_dl_lookup_args *args = (struct call_dl_lookup_args *) ptr;
- args->map = GLRO(dl_lookup_symbol_x) (args->name, args->map, args->refp,
- args->map->l_scope, args->vers, 0,
- args->flags, NULL);
-}
-
-
-static void *
-internal_function
-do_sym (void *handle, const char *name, void *who,
- struct r_found_version *vers, int flags)
-{
- const ElfW(Sym) *ref = NULL;
- lookup_t result;
- ElfW(Addr) caller = (ElfW(Addr)) who;
-
- struct link_map *l = _dl_find_dso_for_object (caller);
- /* If the address is not recognized the call comes from the main
- program (we hope). */
- struct link_map *match = l ? l : GL(dl_ns)[LM_ID_BASE]._ns_loaded;
-
- if (handle == RTLD_DEFAULT)
- {
- /* Search the global scope. We have the simple case where
- we look up in the scope of an object which was part of
- the initial binary. And then the more complex part
- where the object is dynamically loaded and the scope
- array can change. */
- if (RTLD_SINGLE_THREAD_P)
- result = GLRO(dl_lookup_symbol_x) (name, match, &ref,
- match->l_scope, vers, 0,
- flags | DL_LOOKUP_ADD_DEPENDENCY,
- NULL);
- else
- {
- struct call_dl_lookup_args args;
- args.name = name;
- args.map = match;
- args.vers = vers;
- args.flags
- = flags | DL_LOOKUP_ADD_DEPENDENCY | DL_LOOKUP_GSCOPE_LOCK;
- args.refp = &ref;
-
- THREAD_GSCOPE_SET_FLAG ();
-
- const char *objname;
- const char *errstring = NULL;
- bool malloced;
- int err = _dl_catch_error (&objname, &errstring, &malloced,
- call_dl_lookup, &args);
-
- THREAD_GSCOPE_RESET_FLAG ();
-
- if (__glibc_unlikely (errstring != NULL))
- {
- /* The lookup was unsuccessful. Rethrow the error. */
- char *errstring_dup = strdupa (errstring);
- char *objname_dup = strdupa (objname);
- if (malloced)
- free ((char *) errstring);
-
- _dl_signal_error (err, objname_dup, NULL, errstring_dup);
- /* NOTREACHED */
- }
-
- result = args.map;
- }
- }
- else if (handle == RTLD_NEXT)
- {
- if (__glibc_unlikely (match == GL(dl_ns)[LM_ID_BASE]._ns_loaded))
- {
- if (match == NULL
- || caller < match->l_map_start
- || caller >= match->l_map_end)
- _dl_signal_error (0, NULL, NULL, N_("\
-RTLD_NEXT used in code not dynamically loaded"));
- }
-
- struct link_map *l = match;
- while (l->l_loader != NULL)
- l = l->l_loader;
-
- result = GLRO(dl_lookup_symbol_x) (name, match, &ref, l->l_local_scope,
- vers, 0, 0, match);
- }
- else
- {
- /* Search the scope of the given object. */
- struct link_map *map = handle;
- result = GLRO(dl_lookup_symbol_x) (name, map, &ref, map->l_local_scope,
- vers, 0, flags, NULL);
- }
-
- if (ref != NULL)
- {
- void *value;
-
-#ifdef SHARED
- if (ELFW(ST_TYPE) (ref->st_info) == STT_TLS)
- /* The found symbol is a thread-local storage variable.
- Return the address for to the current thread. */
- value = _dl_tls_symaddr (result, ref);
- else
-#endif
- value = DL_SYMBOL_ADDRESS (result, ref);
-
- /* Resolve indirect function address. */
- if (__glibc_unlikely (ELFW(ST_TYPE) (ref->st_info) == STT_GNU_IFUNC))
- {
- DL_FIXUP_VALUE_TYPE fixup
- = DL_FIXUP_MAKE_VALUE (result, (ElfW(Addr)) value);
- fixup = elf_ifunc_invoke (DL_FIXUP_VALUE_ADDR (fixup));
- value = (void *) DL_FIXUP_VALUE_CODE_ADDR (fixup);
- }
-
-#ifdef SHARED
- /* Auditing checkpoint: we have a new binding. Provide the
- auditing libraries the possibility to change the value and
- tell us whether further auditing is wanted. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- const char *strtab = (const char *) D_PTR (result,
- l_info[DT_STRTAB]);
- /* Compute index of the symbol entry in the symbol table of
- the DSO with the definition. */
- unsigned int ndx = (ref - (ElfW(Sym) *) D_PTR (result,
- l_info[DT_SYMTAB]));
-
- if ((match->l_audit_any_plt | result->l_audit_any_plt) != 0)
- {
- unsigned int altvalue = 0;
- struct audit_ifaces *afct = GLRO(dl_audit);
- /* Synthesize a symbol record where the st_value field is
- the result. */
- ElfW(Sym) sym = *ref;
- sym.st_value = (ElfW(Addr)) value;
-
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->symbind != NULL
- && ((match->l_audit[cnt].bindflags & LA_FLG_BINDFROM)
- != 0
- || ((result->l_audit[cnt].bindflags & LA_FLG_BINDTO)
- != 0)))
- {
- unsigned int flags = altvalue | LA_SYMB_DLSYM;
- uintptr_t new_value
- = afct->symbind (&sym, ndx,
- &match->l_audit[cnt].cookie,
- &result->l_audit[cnt].cookie,
- &flags, strtab + ref->st_name);
- if (new_value != (uintptr_t) sym.st_value)
- {
- altvalue = LA_SYMB_ALTVALUE;
- sym.st_value = new_value;
- }
- }
-
- afct = afct->next;
- }
-
- value = (void *) sym.st_value;
- }
- }
-#endif
-
- return value;
- }
-
- return NULL;
-}
-
-
-void *
-internal_function
-_dl_vsym (void *handle, const char *name, const char *version, void *who)
-{
- struct r_found_version vers;
-
- /* Compute hash value to the version string. */
- vers.name = version;
- vers.hidden = 1;
- vers.hash = _dl_elf_hash (version);
- /* We don't have a specific file where the symbol can be found. */
- vers.filename = NULL;
-
- return do_sym (handle, name, who, &vers, 0);
-}
-
-
-void *
-internal_function
-_dl_sym (void *handle, const char *name, void *who)
-{
- return do_sym (handle, name, who, NULL, DL_LOOKUP_RETURN_NEWEST);
-}
diff --git a/elf/dl-symaddr.c b/elf/dl-symaddr.c
deleted file mode 100644
index 5caed4ba21..0000000000
--- a/elf/dl-symaddr.c
+++ /dev/null
@@ -1,33 +0,0 @@
-/* Get the symbol address. Generic version.
- Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <ldsodefs.h>
-#include <dl-fptr.h>
-
-void *
-_dl_symbol_address (struct link_map *map, const ElfW(Sym) *ref)
-{
- ElfW(Addr) value = (map ? map->l_addr : 0) + ref->st_value;
-
- /* Return the pointer to function descriptor. */
- if (ELFW(ST_TYPE) (ref->st_info) == STT_FUNC)
- return (void *) _dl_make_fptr (map, ref, value);
- else
- return (void *) value;
-}
-rtld_hidden_def (_dl_symbol_address)
diff --git a/elf/dl-sysdep-open.h b/elf/dl-sysdep-open.h
deleted file mode 100644
index 91851848b3..0000000000
--- a/elf/dl-sysdep-open.h
+++ /dev/null
@@ -1,45 +0,0 @@
-/* System-specific call to open a shared object by name. Stub version.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _DL_SYSDEP_OPEN_H
-#define _DL_SYSDEP_OPEN_H 1
-
-#include <assert.h>
-#include <stddef.h>
-
-/* NAME is a name without slashes, as it appears in a DT_NEEDED entry
- or a dlopen call's argument or suchlike. NAMELEN is (strlen (NAME) + 1).
-
- Find NAME in an OS-dependent fashion, and return its "real" name.
- Optionally fill in *FD with a file descriptor open on that file (or
- else leave its initial value of -1). The return value is a new
- malloc'd string, which will be free'd by the caller. If NAME is
- resolved to an actual file that can be opened, then the return
- value should name that file (and if *FD was not set, then a normal
- __open call on that string will be made). If *FD was set by some
- other means than a normal open and there is no "real" name to use,
- then __strdup (NAME) is fine (modulo error checking). */
-
-static inline char *
-_dl_sysdep_open_object (const char *name, size_t namelen, int *fd)
-{
- assert (*fd == -1);
- return NULL;
-}
-
-#endif /* dl-sysdep-open.h */
diff --git a/elf/dl-sysdep.c b/elf/dl-sysdep.c
deleted file mode 100644
index 4053ff3c07..0000000000
--- a/elf/dl-sysdep.c
+++ /dev/null
@@ -1,360 +0,0 @@
-/* Operating system support for run-time dynamic linker. Generic Unix version.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* We conditionalize the whole of this file rather than simply eliding it
- from the static build, because other sysdeps/ versions of this file
- might define things needed by a static build. */
-
-#ifdef SHARED
-
-#include <assert.h>
-#include <elf.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <sys/mman.h>
-#include <ldsodefs.h>
-#include <_itoa.h>
-#include <fpu_control.h>
-
-#include <entry.h>
-#include <dl-machine.h>
-#include <dl-procinfo.h>
-#include <dl-osinfo.h>
-#include <hp-timing.h>
-#include <tls.h>
-
-#include <dl-tunables.h>
-
-extern char **_environ attribute_hidden;
-extern char _end[] attribute_hidden;
-
-/* Protect SUID program against misuse of file descriptors. */
-extern void __libc_check_standard_fds (void);
-
-#ifdef NEED_DL_BASE_ADDR
-ElfW(Addr) _dl_base_addr;
-#endif
-int __libc_enable_secure attribute_relro = 0;
-rtld_hidden_data_def (__libc_enable_secure)
-int __libc_multiple_libcs = 0; /* Defining this here avoids the inclusion
- of init-first. */
-/* This variable contains the lowest stack address ever used. */
-void *__libc_stack_end attribute_relro = NULL;
-rtld_hidden_data_def(__libc_stack_end)
-void *_dl_random attribute_relro = NULL;
-
-#ifndef DL_FIND_ARG_COMPONENTS
-# define DL_FIND_ARG_COMPONENTS(cookie, argc, argv, envp, auxp) \
- do { \
- void **_tmp; \
- (argc) = *(long int *) cookie; \
- (argv) = (char **) ((long int *) cookie + 1); \
- (envp) = (argv) + (argc) + 1; \
- for (_tmp = (void **) (envp); *_tmp; ++_tmp) \
- continue; \
- (auxp) = (void *) ++_tmp; \
- } while (0)
-#endif
-
-#ifndef DL_STACK_END
-# define DL_STACK_END(cookie) ((void *) (cookie))
-#endif
-
-ElfW(Addr)
-_dl_sysdep_start (void **start_argptr,
- void (*dl_main) (const ElfW(Phdr) *phdr, ElfW(Word) phnum,
- ElfW(Addr) *user_entry, ElfW(auxv_t) *auxv))
-{
- const ElfW(Phdr) *phdr = NULL;
- ElfW(Word) phnum = 0;
- ElfW(Addr) user_entry;
- ElfW(auxv_t) *av;
-#ifdef HAVE_AUX_SECURE
-# define set_seen(tag) (tag) /* Evaluate for the side effects. */
-# define set_seen_secure() ((void) 0)
-#else
- uid_t uid = 0;
- gid_t gid = 0;
- unsigned int seen = 0;
-# define set_seen_secure() (seen = -1)
-# ifdef HAVE_AUX_XID
-# define set_seen(tag) (tag) /* Evaluate for the side effects. */
-# else
-# define M(type) (1 << (type))
-# define set_seen(tag) seen |= M ((tag)->a_type)
-# endif
-#endif
-#ifdef NEED_DL_SYSINFO
- uintptr_t new_sysinfo = 0;
-#endif
-
- __libc_stack_end = DL_STACK_END (start_argptr);
- DL_FIND_ARG_COMPONENTS (start_argptr, _dl_argc, _dl_argv, _environ,
- GLRO(dl_auxv));
-
- user_entry = (ElfW(Addr)) ENTRY_POINT;
- GLRO(dl_platform) = NULL; /* Default to nothing known about the platform. */
-
- for (av = GLRO(dl_auxv); av->a_type != AT_NULL; set_seen (av++))
- switch (av->a_type)
- {
- case AT_PHDR:
- phdr = (void *) av->a_un.a_val;
- break;
- case AT_PHNUM:
- phnum = av->a_un.a_val;
- break;
- case AT_PAGESZ:
- GLRO(dl_pagesize) = av->a_un.a_val;
- break;
- case AT_ENTRY:
- user_entry = av->a_un.a_val;
- break;
-#ifdef NEED_DL_BASE_ADDR
- case AT_BASE:
- _dl_base_addr = av->a_un.a_val;
- break;
-#endif
-#ifndef HAVE_AUX_SECURE
- case AT_UID:
- case AT_EUID:
- uid ^= av->a_un.a_val;
- break;
- case AT_GID:
- case AT_EGID:
- gid ^= av->a_un.a_val;
- break;
-#endif
- case AT_SECURE:
-#ifndef HAVE_AUX_SECURE
- seen = -1;
-#endif
- __libc_enable_secure = av->a_un.a_val;
- break;
- case AT_PLATFORM:
- GLRO(dl_platform) = (void *) av->a_un.a_val;
- break;
- case AT_HWCAP:
- GLRO(dl_hwcap) = (unsigned long int) av->a_un.a_val;
- break;
- case AT_HWCAP2:
- GLRO(dl_hwcap2) = (unsigned long int) av->a_un.a_val;
- break;
- case AT_CLKTCK:
- GLRO(dl_clktck) = av->a_un.a_val;
- break;
- case AT_FPUCW:
- GLRO(dl_fpu_control) = av->a_un.a_val;
- break;
-#ifdef NEED_DL_SYSINFO
- case AT_SYSINFO:
- new_sysinfo = av->a_un.a_val;
- break;
-#endif
-#ifdef NEED_DL_SYSINFO_DSO
- case AT_SYSINFO_EHDR:
- GLRO(dl_sysinfo_dso) = (void *) av->a_un.a_val;
- break;
-#endif
- case AT_RANDOM:
- _dl_random = (void *) av->a_un.a_val;
- break;
-#ifdef DL_PLATFORM_AUXV
- DL_PLATFORM_AUXV
-#endif
- }
-
-#ifndef HAVE_AUX_SECURE
- if (seen != -1)
- {
- /* Fill in the values we have not gotten from the kernel through the
- auxiliary vector. */
-# ifndef HAVE_AUX_XID
-# define SEE(UID, var, uid) \
- if ((seen & M (AT_##UID)) == 0) var ^= __get##uid ()
- SEE (UID, uid, uid);
- SEE (EUID, uid, euid);
- SEE (GID, gid, gid);
- SEE (EGID, gid, egid);
-# endif
-
- /* If one of the two pairs of IDs does not match this is a setuid
- or setgid run. */
- __libc_enable_secure = uid | gid;
- }
-#endif
-
-#ifndef HAVE_AUX_PAGESIZE
- if (GLRO(dl_pagesize) == 0)
- GLRO(dl_pagesize) = __getpagesize ();
-#endif
-
-#ifdef NEED_DL_SYSINFO
- if (new_sysinfo != 0)
- {
-# ifdef NEED_DL_SYSINFO_DSO
- /* Only set the sysinfo value if we also have the vsyscall DSO. */
- if (GLRO(dl_sysinfo_dso) != 0)
-# endif
- GLRO(dl_sysinfo) = new_sysinfo;
- }
-#endif
-
- __tunables_init (_environ);
-
-#ifdef DL_SYSDEP_INIT
- DL_SYSDEP_INIT;
-#endif
-
-#ifdef DL_PLATFORM_INIT
- DL_PLATFORM_INIT;
-#endif
-
- /* Determine the length of the platform name. */
- if (GLRO(dl_platform) != NULL)
- GLRO(dl_platformlen) = strlen (GLRO(dl_platform));
-
- if (__sbrk (0) == _end)
- /* The dynamic linker was run as a program, and so the initial break
- starts just after our bss, at &_end. The malloc in dl-minimal.c
- will consume the rest of this page, so tell the kernel to move the
- break up that far. When the user program examines its break, it
- will see this new value and not clobber our data. */
- __sbrk (GLRO(dl_pagesize)
- - ((_end - (char *) 0) & (GLRO(dl_pagesize) - 1)));
-
- /* If this is a SUID program we make sure that FDs 0, 1, and 2 are
- allocated. If necessary we are doing it ourself. If it is not
- possible we stop the program. */
- if (__builtin_expect (__libc_enable_secure, 0))
- __libc_check_standard_fds ();
-
- (*dl_main) (phdr, phnum, &user_entry, GLRO(dl_auxv));
- return user_entry;
-}
-
-void
-internal_function
-_dl_sysdep_start_cleanup (void)
-{
-}
-
-void
-internal_function
-_dl_show_auxv (void)
-{
- char buf[64];
- ElfW(auxv_t) *av;
-
- /* Terminate string. */
- buf[63] = '\0';
-
- /* The following code assumes that the AT_* values are encoded
- starting from 0 with AT_NULL, 1 for AT_IGNORE, and all other values
- close by (otherwise the array will be too large). In case we have
- to support a platform where these requirements are not fulfilled
- some alternative implementation has to be used. */
- for (av = GLRO(dl_auxv); av->a_type != AT_NULL; ++av)
- {
- static const struct
- {
- const char label[17];
- enum { unknown = 0, dec, hex, str, ignore } form : 8;
- } auxvars[] =
- {
- [AT_EXECFD - 2] = { "EXECFD: ", dec },
- [AT_EXECFN - 2] = { "EXECFN: ", str },
- [AT_PHDR - 2] = { "PHDR: 0x", hex },
- [AT_PHENT - 2] = { "PHENT: ", dec },
- [AT_PHNUM - 2] = { "PHNUM: ", dec },
- [AT_PAGESZ - 2] = { "PAGESZ: ", dec },
- [AT_BASE - 2] = { "BASE: 0x", hex },
- [AT_FLAGS - 2] = { "FLAGS: 0x", hex },
- [AT_ENTRY - 2] = { "ENTRY: 0x", hex },
- [AT_NOTELF - 2] = { "NOTELF: ", hex },
- [AT_UID - 2] = { "UID: ", dec },
- [AT_EUID - 2] = { "EUID: ", dec },
- [AT_GID - 2] = { "GID: ", dec },
- [AT_EGID - 2] = { "EGID: ", dec },
- [AT_PLATFORM - 2] = { "PLATFORM: ", str },
- [AT_HWCAP - 2] = { "HWCAP: ", hex },
- [AT_CLKTCK - 2] = { "CLKTCK: ", dec },
- [AT_FPUCW - 2] = { "FPUCW: ", hex },
- [AT_DCACHEBSIZE - 2] = { "DCACHEBSIZE: 0x", hex },
- [AT_ICACHEBSIZE - 2] = { "ICACHEBSIZE: 0x", hex },
- [AT_UCACHEBSIZE - 2] = { "UCACHEBSIZE: 0x", hex },
- [AT_IGNOREPPC - 2] = { "IGNOREPPC", ignore },
- [AT_SECURE - 2] = { "SECURE: ", dec },
- [AT_BASE_PLATFORM - 2] = { "BASE_PLATFORM:", str },
- [AT_SYSINFO - 2] = { "SYSINFO: 0x", hex },
- [AT_SYSINFO_EHDR - 2] = { "SYSINFO_EHDR: 0x", hex },
- [AT_RANDOM - 2] = { "RANDOM: 0x", hex },
- [AT_HWCAP2 - 2] = { "HWCAP2: 0x", hex },
- };
- unsigned int idx = (unsigned int) (av->a_type - 2);
-
- if ((unsigned int) av->a_type < 2u
- || (idx < sizeof (auxvars) / sizeof (auxvars[0])
- && auxvars[idx].form == ignore))
- continue;
-
- assert (AT_NULL == 0);
- assert (AT_IGNORE == 1);
-
- if (av->a_type == AT_HWCAP || av->a_type == AT_HWCAP2)
- {
- /* These are handled in a special way per platform. */
- if (_dl_procinfo (av->a_type, av->a_un.a_val) == 0)
- continue;
- }
-
- if (idx < sizeof (auxvars) / sizeof (auxvars[0])
- && auxvars[idx].form != unknown)
- {
- const char *val = (char *) av->a_un.a_val;
-
- if (__builtin_expect (auxvars[idx].form, dec) == dec)
- val = _itoa ((unsigned long int) av->a_un.a_val,
- buf + sizeof buf - 1, 10, 0);
- else if (__builtin_expect (auxvars[idx].form, hex) == hex)
- val = _itoa ((unsigned long int) av->a_un.a_val,
- buf + sizeof buf - 1, 16, 0);
-
- _dl_printf ("AT_%s%s\n", auxvars[idx].label, val);
-
- continue;
- }
-
- /* Unknown value: print a generic line. */
- char buf2[17];
- buf2[sizeof (buf2) - 1] = '\0';
- const char *val2 = _itoa ((unsigned long int) av->a_un.a_val,
- buf2 + sizeof buf2 - 1, 16, 0);
- const char *val = _itoa ((unsigned long int) av->a_type,
- buf + sizeof buf - 1, 16, 0);
- _dl_printf ("AT_??? (0x%s): 0x%s\n", val, val2);
- }
-}
-
-#endif
diff --git a/elf/dl-tls.c b/elf/dl-tls.c
deleted file mode 100644
index 5aba33b3fa..0000000000
--- a/elf/dl-tls.c
+++ /dev/null
@@ -1,953 +0,0 @@
-/* Thread-local storage handling in the ELF dynamic linker. Generic version.
- Copyright (C) 2002-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <assert.h>
-#include <errno.h>
-#include <libintl.h>
-#include <signal.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <sys/param.h>
-#include <atomic.h>
-
-#include <tls.h>
-#include <dl-tls.h>
-#include <ldsodefs.h>
-
-/* Amount of excess space to allocate in the static TLS area
- to allow dynamic loading of modules defining IE-model TLS data. */
-#define TLS_STATIC_SURPLUS 64 + DL_NNS * 100
-
-
-/* Out-of-memory handler. */
-static void
-__attribute__ ((__noreturn__))
-oom (void)
-{
- _dl_fatal_printf ("cannot allocate memory for thread-local data: ABORT\n");
-}
-
-
-size_t
-internal_function
-_dl_next_tls_modid (void)
-{
- size_t result;
-
- if (__builtin_expect (GL(dl_tls_dtv_gaps), false))
- {
- size_t disp = 0;
- struct dtv_slotinfo_list *runp = GL(dl_tls_dtv_slotinfo_list);
-
- /* Note that this branch will never be executed during program
- start since there are no gaps at that time. Therefore it
- does not matter that the dl_tls_dtv_slotinfo is not allocated
- yet when the function is called for the first times.
-
- NB: the offset +1 is due to the fact that DTV[0] is used
- for something else. */
- result = GL(dl_tls_static_nelem) + 1;
- if (result <= GL(dl_tls_max_dtv_idx))
- do
- {
- while (result - disp < runp->len)
- {
- if (runp->slotinfo[result - disp].map == NULL)
- break;
-
- ++result;
- assert (result <= GL(dl_tls_max_dtv_idx) + 1);
- }
-
- if (result - disp < runp->len)
- break;
-
- disp += runp->len;
- }
- while ((runp = runp->next) != NULL);
-
- if (result > GL(dl_tls_max_dtv_idx))
- {
- /* The new index must indeed be exactly one higher than the
- previous high. */
- assert (result == GL(dl_tls_max_dtv_idx) + 1);
- /* There is no gap anymore. */
- GL(dl_tls_dtv_gaps) = false;
-
- goto nogaps;
- }
- }
- else
- {
- /* No gaps, allocate a new entry. */
- nogaps:
-
- result = ++GL(dl_tls_max_dtv_idx);
- }
-
- return result;
-}
-
-
-size_t
-internal_function
-_dl_count_modids (void)
-{
- /* It is rare that we have gaps; see elf/dl-open.c (_dl_open) where
- we fail to load a module and unload it leaving a gap. If we don't
- have gaps then the number of modids is the current maximum so
- return that. */
- if (__glibc_likely (!GL(dl_tls_dtv_gaps)))
- return GL(dl_tls_max_dtv_idx);
-
- /* We have gaps and are forced to count the non-NULL entries. */
- size_t n = 0;
- struct dtv_slotinfo_list *runp = GL(dl_tls_dtv_slotinfo_list);
- while (runp != NULL)
- {
- for (size_t i = 0; i < runp->len; ++i)
- if (runp->slotinfo[i].map != NULL)
- ++n;
-
- runp = runp->next;
- }
-
- return n;
-}
-
-
-#ifdef SHARED
-void
-internal_function
-_dl_determine_tlsoffset (void)
-{
- size_t max_align = TLS_TCB_ALIGN;
- size_t freetop = 0;
- size_t freebottom = 0;
-
- /* The first element of the dtv slot info list is allocated. */
- assert (GL(dl_tls_dtv_slotinfo_list) != NULL);
- /* There is at this point only one element in the
- dl_tls_dtv_slotinfo_list list. */
- assert (GL(dl_tls_dtv_slotinfo_list)->next == NULL);
-
- struct dtv_slotinfo *slotinfo = GL(dl_tls_dtv_slotinfo_list)->slotinfo;
-
- /* Determining the offset of the various parts of the static TLS
- block has several dependencies. In addition we have to work
- around bugs in some toolchains.
-
- Each TLS block from the objects available at link time has a size
- and an alignment requirement. The GNU ld computes the alignment
- requirements for the data at the positions *in the file*, though.
- I.e, it is not simply possible to allocate a block with the size
- of the TLS program header entry. The data is layed out assuming
- that the first byte of the TLS block fulfills
-
- p_vaddr mod p_align == &TLS_BLOCK mod p_align
-
- This means we have to add artificial padding at the beginning of
- the TLS block. These bytes are never used for the TLS data in
- this module but the first byte allocated must be aligned
- according to mod p_align == 0 so that the first byte of the TLS
- block is aligned according to p_vaddr mod p_align. This is ugly
- and the linker can help by computing the offsets in the TLS block
- assuming the first byte of the TLS block is aligned according to
- p_align.
-
- The extra space which might be allocated before the first byte of
- the TLS block need not go unused. The code below tries to use
- that memory for the next TLS block. This can work if the total
- memory requirement for the next TLS block is smaller than the
- gap. */
-
-#if TLS_TCB_AT_TP
- /* We simply start with zero. */
- size_t offset = 0;
-
- for (size_t cnt = 0; slotinfo[cnt].map != NULL; ++cnt)
- {
- assert (cnt < GL(dl_tls_dtv_slotinfo_list)->len);
-
- size_t firstbyte = (-slotinfo[cnt].map->l_tls_firstbyte_offset
- & (slotinfo[cnt].map->l_tls_align - 1));
- size_t off;
- max_align = MAX (max_align, slotinfo[cnt].map->l_tls_align);
-
- if (freebottom - freetop >= slotinfo[cnt].map->l_tls_blocksize)
- {
- off = roundup (freetop + slotinfo[cnt].map->l_tls_blocksize
- - firstbyte, slotinfo[cnt].map->l_tls_align)
- + firstbyte;
- if (off <= freebottom)
- {
- freetop = off;
-
- /* XXX For some architectures we perhaps should store the
- negative offset. */
- slotinfo[cnt].map->l_tls_offset = off;
- continue;
- }
- }
-
- off = roundup (offset + slotinfo[cnt].map->l_tls_blocksize - firstbyte,
- slotinfo[cnt].map->l_tls_align) + firstbyte;
- if (off > offset + slotinfo[cnt].map->l_tls_blocksize
- + (freebottom - freetop))
- {
- freetop = offset;
- freebottom = off - slotinfo[cnt].map->l_tls_blocksize;
- }
- offset = off;
-
- /* XXX For some architectures we perhaps should store the
- negative offset. */
- slotinfo[cnt].map->l_tls_offset = off;
- }
-
- GL(dl_tls_static_used) = offset;
- GL(dl_tls_static_size) = (roundup (offset + TLS_STATIC_SURPLUS, max_align)
- + TLS_TCB_SIZE);
-#elif TLS_DTV_AT_TP
- /* The TLS blocks start right after the TCB. */
- size_t offset = TLS_TCB_SIZE;
-
- for (size_t cnt = 0; slotinfo[cnt].map != NULL; ++cnt)
- {
- assert (cnt < GL(dl_tls_dtv_slotinfo_list)->len);
-
- size_t firstbyte = (-slotinfo[cnt].map->l_tls_firstbyte_offset
- & (slotinfo[cnt].map->l_tls_align - 1));
- size_t off;
- max_align = MAX (max_align, slotinfo[cnt].map->l_tls_align);
-
- if (slotinfo[cnt].map->l_tls_blocksize <= freetop - freebottom)
- {
- off = roundup (freebottom, slotinfo[cnt].map->l_tls_align);
- if (off - freebottom < firstbyte)
- off += slotinfo[cnt].map->l_tls_align;
- if (off + slotinfo[cnt].map->l_tls_blocksize - firstbyte <= freetop)
- {
- slotinfo[cnt].map->l_tls_offset = off - firstbyte;
- freebottom = (off + slotinfo[cnt].map->l_tls_blocksize
- - firstbyte);
- continue;
- }
- }
-
- off = roundup (offset, slotinfo[cnt].map->l_tls_align);
- if (off - offset < firstbyte)
- off += slotinfo[cnt].map->l_tls_align;
-
- slotinfo[cnt].map->l_tls_offset = off - firstbyte;
- if (off - firstbyte - offset > freetop - freebottom)
- {
- freebottom = offset;
- freetop = off - firstbyte;
- }
-
- offset = off + slotinfo[cnt].map->l_tls_blocksize - firstbyte;
- }
-
- GL(dl_tls_static_used) = offset;
- GL(dl_tls_static_size) = roundup (offset + TLS_STATIC_SURPLUS,
- TLS_TCB_ALIGN);
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
-
- /* The alignment requirement for the static TLS block. */
- GL(dl_tls_static_align) = max_align;
-}
-#endif /* SHARED */
-
-static void *
-internal_function
-allocate_dtv (void *result)
-{
- dtv_t *dtv;
- size_t dtv_length;
-
- /* We allocate a few more elements in the dtv than are needed for the
- initial set of modules. This should avoid in most cases expansions
- of the dtv. */
- dtv_length = GL(dl_tls_max_dtv_idx) + DTV_SURPLUS;
- dtv = calloc (dtv_length + 2, sizeof (dtv_t));
- if (dtv != NULL)
- {
- /* This is the initial length of the dtv. */
- dtv[0].counter = dtv_length;
-
- /* The rest of the dtv (including the generation counter) is
- Initialize with zero to indicate nothing there. */
-
- /* Add the dtv to the thread data structures. */
- INSTALL_DTV (result, dtv);
- }
- else
- result = NULL;
-
- return result;
-}
-
-
-/* Get size and alignment requirements of the static TLS block. */
-void
-internal_function
-_dl_get_tls_static_info (size_t *sizep, size_t *alignp)
-{
- *sizep = GL(dl_tls_static_size);
- *alignp = GL(dl_tls_static_align);
-}
-
-/* Derive the location of the pointer to the start of the original
- allocation (before alignment) from the pointer to the TCB. */
-static inline void **
-tcb_to_pointer_to_free_location (void *tcb)
-{
-#if TLS_TCB_AT_TP
- /* The TCB follows the TLS blocks, and the pointer to the front
- follows the TCB. */
- void **original_pointer_location = tcb + TLS_TCB_SIZE;
-#elif TLS_DTV_AT_TP
- /* The TCB comes first, preceded by the pre-TCB, and the pointer is
- before that. */
- void **original_pointer_location = tcb - TLS_PRE_TCB_SIZE - sizeof (void *);
-#endif
- return original_pointer_location;
-}
-
-void *
-internal_function
-_dl_allocate_tls_storage (void)
-{
- void *result;
- size_t size = GL(dl_tls_static_size);
-
-#if TLS_DTV_AT_TP
- /* Memory layout is:
- [ TLS_PRE_TCB_SIZE ] [ TLS_TCB_SIZE ] [ TLS blocks ]
- ^ This should be returned. */
- size += TLS_PRE_TCB_SIZE;
-#endif
-
- /* Perform the allocation. Reserve space for the required alignment
- and the pointer to the original allocation. */
- size_t alignment = GL(dl_tls_static_align);
- void *allocated = malloc (size + alignment + sizeof (void *));
- if (__glibc_unlikely (allocated == NULL))
- return NULL;
-
- /* Perform alignment and allocate the DTV. */
-#if TLS_TCB_AT_TP
- /* The TCB follows the TLS blocks, which determine the alignment.
- (TCB alignment requirements have been taken into account when
- calculating GL(dl_tls_static_align).) */
- void *aligned = (void *) roundup ((uintptr_t) allocated, alignment);
- result = aligned + size - TLS_TCB_SIZE;
-
- /* Clear the TCB data structure. We can't ask the caller (i.e.
- libpthread) to do it, because we will initialize the DTV et al. */
- memset (result, '\0', TLS_TCB_SIZE);
-#elif TLS_DTV_AT_TP
- /* Pre-TCB and TCB come before the TLS blocks. The layout computed
- in _dl_determine_tlsoffset assumes that the TCB is aligned to the
- TLS block alignment, and not just the TLS blocks after it. This
- can leave an unused alignment gap between the TCB and the TLS
- blocks. */
- result = (void *) roundup
- (sizeof (void *) + TLS_PRE_TCB_SIZE + (uintptr_t) allocated,
- alignment);
-
- /* Clear the TCB data structure and TLS_PRE_TCB_SIZE bytes before
- it. We can't ask the caller (i.e. libpthread) to do it, because
- we will initialize the DTV et al. */
- memset (result - TLS_PRE_TCB_SIZE, '\0', TLS_PRE_TCB_SIZE + TLS_TCB_SIZE);
-#endif
-
- /* Record the value of the original pointer for later
- deallocation. */
- *tcb_to_pointer_to_free_location (result) = allocated;
-
- result = allocate_dtv (result);
- if (result == NULL)
- free (allocated);
- return result;
-}
-
-
-#ifndef SHARED
-extern dtv_t _dl_static_dtv[];
-# define _dl_initial_dtv (&_dl_static_dtv[1])
-#endif
-
-static dtv_t *
-_dl_resize_dtv (dtv_t *dtv)
-{
- /* Resize the dtv. */
- dtv_t *newp;
- /* Load GL(dl_tls_max_dtv_idx) atomically since it may be written to by
- other threads concurrently. */
- size_t newsize
- = atomic_load_acquire (&GL(dl_tls_max_dtv_idx)) + DTV_SURPLUS;
- size_t oldsize = dtv[-1].counter;
-
- if (dtv == GL(dl_initial_dtv))
- {
- /* This is the initial dtv that was either statically allocated in
- __libc_setup_tls or allocated during rtld startup using the
- dl-minimal.c malloc instead of the real malloc. We can't free
- it, we have to abandon the old storage. */
-
- newp = malloc ((2 + newsize) * sizeof (dtv_t));
- if (newp == NULL)
- oom ();
- memcpy (newp, &dtv[-1], (2 + oldsize) * sizeof (dtv_t));
- }
- else
- {
- newp = realloc (&dtv[-1],
- (2 + newsize) * sizeof (dtv_t));
- if (newp == NULL)
- oom ();
- }
-
- newp[0].counter = newsize;
-
- /* Clear the newly allocated part. */
- memset (newp + 2 + oldsize, '\0',
- (newsize - oldsize) * sizeof (dtv_t));
-
- /* Return the generation counter. */
- return &newp[1];
-}
-
-
-void *
-internal_function
-_dl_allocate_tls_init (void *result)
-{
- if (result == NULL)
- /* The memory allocation failed. */
- return NULL;
-
- dtv_t *dtv = GET_DTV (result);
- struct dtv_slotinfo_list *listp;
- size_t total = 0;
- size_t maxgen = 0;
-
- /* Check if the current dtv is big enough. */
- if (dtv[-1].counter < GL(dl_tls_max_dtv_idx))
- {
- /* Resize the dtv. */
- dtv = _dl_resize_dtv (dtv);
-
- /* Install this new dtv in the thread data structures. */
- INSTALL_DTV (result, &dtv[-1]);
- }
-
- /* We have to prepare the dtv for all currently loaded modules using
- TLS. For those which are dynamically loaded we add the values
- indicating deferred allocation. */
- listp = GL(dl_tls_dtv_slotinfo_list);
- while (1)
- {
- size_t cnt;
-
- for (cnt = total == 0 ? 1 : 0; cnt < listp->len; ++cnt)
- {
- struct link_map *map;
- void *dest;
-
- /* Check for the total number of used slots. */
- if (total + cnt > GL(dl_tls_max_dtv_idx))
- break;
-
- map = listp->slotinfo[cnt].map;
- if (map == NULL)
- /* Unused entry. */
- continue;
-
- /* Keep track of the maximum generation number. This might
- not be the generation counter. */
- assert (listp->slotinfo[cnt].gen <= GL(dl_tls_generation));
- maxgen = MAX (maxgen, listp->slotinfo[cnt].gen);
-
- dtv[map->l_tls_modid].pointer.val = TLS_DTV_UNALLOCATED;
- dtv[map->l_tls_modid].pointer.to_free = NULL;
-
- if (map->l_tls_offset == NO_TLS_OFFSET
- || map->l_tls_offset == FORCED_DYNAMIC_TLS_OFFSET)
- continue;
-
- assert (map->l_tls_modid == total + cnt);
- assert (map->l_tls_blocksize >= map->l_tls_initimage_size);
-#if TLS_TCB_AT_TP
- assert ((size_t) map->l_tls_offset >= map->l_tls_blocksize);
- dest = (char *) result - map->l_tls_offset;
-#elif TLS_DTV_AT_TP
- dest = (char *) result + map->l_tls_offset;
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
-
- /* Set up the DTV entry. The simplified __tls_get_addr that
- some platforms use in static programs requires it. */
- dtv[map->l_tls_modid].pointer.val = dest;
-
- /* Copy the initialization image and clear the BSS part. */
- memset (__mempcpy (dest, map->l_tls_initimage,
- map->l_tls_initimage_size), '\0',
- map->l_tls_blocksize - map->l_tls_initimage_size);
- }
-
- total += cnt;
- if (total >= GL(dl_tls_max_dtv_idx))
- break;
-
- listp = listp->next;
- assert (listp != NULL);
- }
-
- /* The DTV version is up-to-date now. */
- dtv[0].counter = maxgen;
-
- return result;
-}
-rtld_hidden_def (_dl_allocate_tls_init)
-
-void *
-internal_function
-_dl_allocate_tls (void *mem)
-{
- return _dl_allocate_tls_init (mem == NULL
- ? _dl_allocate_tls_storage ()
- : allocate_dtv (mem));
-}
-rtld_hidden_def (_dl_allocate_tls)
-
-
-void
-internal_function
-_dl_deallocate_tls (void *tcb, bool dealloc_tcb)
-{
- dtv_t *dtv = GET_DTV (tcb);
-
- /* We need to free the memory allocated for non-static TLS. */
- for (size_t cnt = 0; cnt < dtv[-1].counter; ++cnt)
- free (dtv[1 + cnt].pointer.to_free);
-
- /* The array starts with dtv[-1]. */
- if (dtv != GL(dl_initial_dtv))
- free (dtv - 1);
-
- if (dealloc_tcb)
- free (*tcb_to_pointer_to_free_location (tcb));
-}
-rtld_hidden_def (_dl_deallocate_tls)
-
-
-#ifdef SHARED
-/* The __tls_get_addr function has two basic forms which differ in the
- arguments. The IA-64 form takes two parameters, the module ID and
- offset. The form used, among others, on IA-32 takes a reference to
- a special structure which contain the same information. The second
- form seems to be more often used (in the moment) so we default to
- it. Users of the IA-64 form have to provide adequate definitions
- of the following macros. */
-# ifndef GET_ADDR_ARGS
-# define GET_ADDR_ARGS tls_index *ti
-# define GET_ADDR_PARAM ti
-# endif
-# ifndef GET_ADDR_MODULE
-# define GET_ADDR_MODULE ti->ti_module
-# endif
-# ifndef GET_ADDR_OFFSET
-# define GET_ADDR_OFFSET ti->ti_offset
-# endif
-
-/* Allocate one DTV entry. */
-static struct dtv_pointer
-allocate_dtv_entry (size_t alignment, size_t size)
-{
- if (powerof2 (alignment) && alignment <= _Alignof (max_align_t))
- {
- /* The alignment is supported by malloc. */
- void *ptr = malloc (size);
- return (struct dtv_pointer) { ptr, ptr };
- }
-
- /* Emulate memalign to by manually aligning a pointer returned by
- malloc. First compute the size with an overflow check. */
- size_t alloc_size = size + alignment;
- if (alloc_size < size)
- return (struct dtv_pointer) {};
-
- /* Perform the allocation. This is the pointer we need to free
- later. */
- void *start = malloc (alloc_size);
- if (start == NULL)
- return (struct dtv_pointer) {};
-
- /* Find the aligned position within the larger allocation. */
- void *aligned = (void *) roundup ((uintptr_t) start, alignment);
-
- return (struct dtv_pointer) { .val = aligned, .to_free = start };
-}
-
-static struct dtv_pointer
-allocate_and_init (struct link_map *map)
-{
- struct dtv_pointer result = allocate_dtv_entry
- (map->l_tls_align, map->l_tls_blocksize);
- if (result.val == NULL)
- oom ();
-
- /* Initialize the memory. */
- memset (__mempcpy (result.val, map->l_tls_initimage,
- map->l_tls_initimage_size),
- '\0', map->l_tls_blocksize - map->l_tls_initimage_size);
-
- return result;
-}
-
-
-struct link_map *
-_dl_update_slotinfo (unsigned long int req_modid)
-{
- struct link_map *the_map = NULL;
- dtv_t *dtv = THREAD_DTV ();
-
- /* The global dl_tls_dtv_slotinfo array contains for each module
- index the generation counter current when the entry was created.
- This array never shrinks so that all module indices which were
- valid at some time can be used to access it. Before the first
- use of a new module index in this function the array was extended
- appropriately. Access also does not have to be guarded against
- modifications of the array. It is assumed that pointer-size
- values can be read atomically even in SMP environments. It is
- possible that other threads at the same time dynamically load
- code and therefore add to the slotinfo list. This is a problem
- since we must not pick up any information about incomplete work.
- The solution to this is to ignore all dtv slots which were
- created after the one we are currently interested. We know that
- dynamic loading for this module is completed and this is the last
- load operation we know finished. */
- unsigned long int idx = req_modid;
- struct dtv_slotinfo_list *listp = GL(dl_tls_dtv_slotinfo_list);
-
- while (idx >= listp->len)
- {
- idx -= listp->len;
- listp = listp->next;
- }
-
- if (dtv[0].counter < listp->slotinfo[idx].gen)
- {
- /* The generation counter for the slot is higher than what the
- current dtv implements. We have to update the whole dtv but
- only those entries with a generation counter <= the one for
- the entry we need. */
- size_t new_gen = listp->slotinfo[idx].gen;
- size_t total = 0;
-
- /* We have to look through the entire dtv slotinfo list. */
- listp = GL(dl_tls_dtv_slotinfo_list);
- do
- {
- for (size_t cnt = total == 0 ? 1 : 0; cnt < listp->len; ++cnt)
- {
- size_t gen = listp->slotinfo[cnt].gen;
-
- if (gen > new_gen)
- /* This is a slot for a generation younger than the
- one we are handling now. It might be incompletely
- set up so ignore it. */
- continue;
-
- /* If the entry is older than the current dtv layout we
- know we don't have to handle it. */
- if (gen <= dtv[0].counter)
- continue;
-
- /* If there is no map this means the entry is empty. */
- struct link_map *map = listp->slotinfo[cnt].map;
- if (map == NULL)
- {
- if (dtv[-1].counter >= total + cnt)
- {
- /* If this modid was used at some point the memory
- might still be allocated. */
- free (dtv[total + cnt].pointer.to_free);
- dtv[total + cnt].pointer.val = TLS_DTV_UNALLOCATED;
- dtv[total + cnt].pointer.to_free = NULL;
- }
-
- continue;
- }
-
- /* Check whether the current dtv array is large enough. */
- size_t modid = map->l_tls_modid;
- assert (total + cnt == modid);
- if (dtv[-1].counter < modid)
- {
- /* Resize the dtv. */
- dtv = _dl_resize_dtv (dtv);
-
- assert (modid <= dtv[-1].counter);
-
- /* Install this new dtv in the thread data
- structures. */
- INSTALL_NEW_DTV (dtv);
- }
-
- /* If there is currently memory allocate for this
- dtv entry free it. */
- /* XXX Ideally we will at some point create a memory
- pool. */
- free (dtv[modid].pointer.to_free);
- dtv[modid].pointer.val = TLS_DTV_UNALLOCATED;
- dtv[modid].pointer.to_free = NULL;
-
- if (modid == req_modid)
- the_map = map;
- }
-
- total += listp->len;
- }
- while ((listp = listp->next) != NULL);
-
- /* This will be the new maximum generation counter. */
- dtv[0].counter = new_gen;
- }
-
- return the_map;
-}
-
-
-static void *
-__attribute_noinline__
-tls_get_addr_tail (GET_ADDR_ARGS, dtv_t *dtv, struct link_map *the_map)
-{
- /* The allocation was deferred. Do it now. */
- if (the_map == NULL)
- {
- /* Find the link map for this module. */
- size_t idx = GET_ADDR_MODULE;
- struct dtv_slotinfo_list *listp = GL(dl_tls_dtv_slotinfo_list);
-
- while (idx >= listp->len)
- {
- idx -= listp->len;
- listp = listp->next;
- }
-
- the_map = listp->slotinfo[idx].map;
- }
-
- /* Make sure that, if a dlopen running in parallel forces the
- variable into static storage, we'll wait until the address in the
- static TLS block is set up, and use that. If we're undecided
- yet, make sure we make the decision holding the lock as well. */
- if (__glibc_unlikely (the_map->l_tls_offset
- != FORCED_DYNAMIC_TLS_OFFSET))
- {
- __rtld_lock_lock_recursive (GL(dl_load_lock));
- if (__glibc_likely (the_map->l_tls_offset == NO_TLS_OFFSET))
- {
- the_map->l_tls_offset = FORCED_DYNAMIC_TLS_OFFSET;
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- }
- else if (__glibc_likely (the_map->l_tls_offset
- != FORCED_DYNAMIC_TLS_OFFSET))
- {
-#if TLS_TCB_AT_TP
- void *p = (char *) THREAD_SELF - the_map->l_tls_offset;
-#elif TLS_DTV_AT_TP
- void *p = (char *) THREAD_SELF + the_map->l_tls_offset + TLS_PRE_TCB_SIZE;
-#else
-# error "Either TLS_TCB_AT_TP or TLS_DTV_AT_TP must be defined"
-#endif
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-
- dtv[GET_ADDR_MODULE].pointer.to_free = NULL;
- dtv[GET_ADDR_MODULE].pointer.val = p;
-
- return (char *) p + GET_ADDR_OFFSET;
- }
- else
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- }
- struct dtv_pointer result = allocate_and_init (the_map);
- dtv[GET_ADDR_MODULE].pointer = result;
- assert (result.to_free != NULL);
-
- return (char *) result.val + GET_ADDR_OFFSET;
-}
-
-
-static struct link_map *
-__attribute_noinline__
-update_get_addr (GET_ADDR_ARGS)
-{
- struct link_map *the_map = _dl_update_slotinfo (GET_ADDR_MODULE);
- dtv_t *dtv = THREAD_DTV ();
-
- void *p = dtv[GET_ADDR_MODULE].pointer.val;
-
- if (__glibc_unlikely (p == TLS_DTV_UNALLOCATED))
- return tls_get_addr_tail (GET_ADDR_PARAM, dtv, the_map);
-
- return (void *) p + GET_ADDR_OFFSET;
-}
-
-/* For all machines that have a non-macro version of __tls_get_addr, we
- want to use rtld_hidden_proto/rtld_hidden_def in order to call the
- internal alias for __tls_get_addr from ld.so. This avoids a PLT entry
- in ld.so for __tls_get_addr. */
-
-#ifndef __tls_get_addr
-extern void * __tls_get_addr (GET_ADDR_ARGS);
-rtld_hidden_proto (__tls_get_addr)
-rtld_hidden_def (__tls_get_addr)
-#endif
-
-/* The generic dynamic and local dynamic model cannot be used in
- statically linked applications. */
-void *
-__tls_get_addr (GET_ADDR_ARGS)
-{
- dtv_t *dtv = THREAD_DTV ();
-
- if (__glibc_unlikely (dtv[0].counter != GL(dl_tls_generation)))
- return update_get_addr (GET_ADDR_PARAM);
-
- void *p = dtv[GET_ADDR_MODULE].pointer.val;
-
- if (__glibc_unlikely (p == TLS_DTV_UNALLOCATED))
- return tls_get_addr_tail (GET_ADDR_PARAM, dtv, NULL);
-
- return (char *) p + GET_ADDR_OFFSET;
-}
-#endif
-
-
-/* Look up the module's TLS block as for __tls_get_addr,
- but never touch anything. Return null if it's not allocated yet. */
-void *
-_dl_tls_get_addr_soft (struct link_map *l)
-{
- if (__glibc_unlikely (l->l_tls_modid == 0))
- /* This module has no TLS segment. */
- return NULL;
-
- dtv_t *dtv = THREAD_DTV ();
- if (__glibc_unlikely (dtv[0].counter != GL(dl_tls_generation)))
- {
- /* This thread's DTV is not completely current,
- but it might already cover this module. */
-
- if (l->l_tls_modid >= dtv[-1].counter)
- /* Nope. */
- return NULL;
-
- size_t idx = l->l_tls_modid;
- struct dtv_slotinfo_list *listp = GL(dl_tls_dtv_slotinfo_list);
- while (idx >= listp->len)
- {
- idx -= listp->len;
- listp = listp->next;
- }
-
- /* We've reached the slot for this module.
- If its generation counter is higher than the DTV's,
- this thread does not know about this module yet. */
- if (dtv[0].counter < listp->slotinfo[idx].gen)
- return NULL;
- }
-
- void *data = dtv[l->l_tls_modid].pointer.val;
- if (__glibc_unlikely (data == TLS_DTV_UNALLOCATED))
- /* The DTV is current, but this thread has not yet needed
- to allocate this module's segment. */
- data = NULL;
-
- return data;
-}
-
-
-void
-_dl_add_to_slotinfo (struct link_map *l)
-{
- /* Now that we know the object is loaded successfully add
- modules containing TLS data to the dtv info table. We
- might have to increase its size. */
- struct dtv_slotinfo_list *listp;
- struct dtv_slotinfo_list *prevp;
- size_t idx = l->l_tls_modid;
-
- /* Find the place in the dtv slotinfo list. */
- listp = GL(dl_tls_dtv_slotinfo_list);
- prevp = NULL; /* Needed to shut up gcc. */
- do
- {
- /* Does it fit in the array of this list element? */
- if (idx < listp->len)
- break;
- idx -= listp->len;
- prevp = listp;
- listp = listp->next;
- }
- while (listp != NULL);
-
- if (listp == NULL)
- {
- /* When we come here it means we have to add a new element
- to the slotinfo list. And the new module must be in
- the first slot. */
- assert (idx == 0);
-
- listp = prevp->next = (struct dtv_slotinfo_list *)
- malloc (sizeof (struct dtv_slotinfo_list)
- + TLS_SLOTINFO_SURPLUS * sizeof (struct dtv_slotinfo));
- if (listp == NULL)
- {
- /* We ran out of memory. We will simply fail this
- call but don't undo anything we did so far. The
- application will crash or be terminated anyway very
- soon. */
-
- /* We have to do this since some entries in the dtv
- slotinfo array might already point to this
- generation. */
- ++GL(dl_tls_generation);
-
- _dl_signal_error (ENOMEM, "dlopen", NULL, N_("\
-cannot create TLS data structures"));
- }
-
- listp->len = TLS_SLOTINFO_SURPLUS;
- listp->next = NULL;
- memset (listp->slotinfo, '\0',
- TLS_SLOTINFO_SURPLUS * sizeof (struct dtv_slotinfo));
- }
-
- /* Add the information into the slotinfo data structure. */
- listp->slotinfo[idx].map = l;
- listp->slotinfo[idx].gen = GL(dl_tls_generation) + 1;
-}
diff --git a/elf/dl-trampoline.c b/elf/dl-trampoline.c
deleted file mode 100644
index 3ca89f3879..0000000000
--- a/elf/dl-trampoline.c
+++ /dev/null
@@ -1 +0,0 @@
-#error "Architecture specific PLT trampolines must be defined."
diff --git a/elf/dl-tunable-types.h b/elf/dl-tunable-types.h
deleted file mode 100644
index 1d516df08f..0000000000
--- a/elf/dl-tunable-types.h
+++ /dev/null
@@ -1,62 +0,0 @@
-/* Tunable type information.
-
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _TUNABLE_TYPES_H_
-# define _TUNABLE_TYPES_H_
-#include <stddef.h>
-
-typedef enum
-{
- TUNABLE_TYPE_INT_32,
- TUNABLE_TYPE_UINT_64,
- TUNABLE_TYPE_SIZE_T,
- TUNABLE_TYPE_STRING
-} tunable_type_code_t;
-
-typedef struct
-{
- tunable_type_code_t type_code;
- int64_t min;
- int64_t max;
-} tunable_type_t;
-
-typedef union
-{
- int64_t numval;
- const char *strval;
-} tunable_val_t;
-
-typedef void (*tunable_callback_t) (tunable_val_t *);
-
-/* Security level for tunables. This decides what to do with individual
- tunables for AT_SECURE binaries. */
-typedef enum
-{
- /* Erase the tunable for AT_SECURE binaries so that child processes don't
- read it. */
- TUNABLE_SECLEVEL_SXID_ERASE = 0,
- /* Ignore the tunable for AT_SECURE binaries, but don't erase it, so that
- child processes can read it. */
- TUNABLE_SECLEVEL_SXID_IGNORE = 1,
- /* Read the tunable. */
- TUNABLE_SECLEVEL_NONE = 2,
-} tunable_seclevel_t;
-
-
-#endif
diff --git a/elf/dl-tunables.c b/elf/dl-tunables.c
deleted file mode 100644
index 76e8c5cae1..0000000000
--- a/elf/dl-tunables.c
+++ /dev/null
@@ -1,490 +0,0 @@
-/* The tunable framework. See the README.tunables to know how to use the
- tunable in a glibc module.
-
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdint.h>
-#include <stdbool.h>
-#include <unistd.h>
-#include <stdlib.h>
-#include <sysdep.h>
-#include <fcntl.h>
-#include <ldsodefs.h>
-
-#define TUNABLES_INTERNAL 1
-#include "dl-tunables.h"
-
-#if TUNABLES_FRONTEND == TUNABLES_FRONTEND_valstring
-# define GLIBC_TUNABLES "GLIBC_TUNABLES"
-#endif
-
-/* Compare environment or tunable names, bounded by the name hardcoded in
- glibc. */
-static bool
-is_name (const char *orig, const char *envname)
-{
- for (;*orig != '\0' && *envname != '\0'; envname++, orig++)
- if (*orig != *envname)
- break;
-
- /* The ENVNAME is immediately followed by a value. */
- if (*orig == '\0' && *envname == '=')
- return true;
- else
- return false;
-}
-
-#if TUNABLES_FRONTEND == TUNABLES_FRONTEND_valstring
-static char *
-tunables_strdup (const char *in)
-{
- size_t i = 0;
-
- while (in[i++] != '\0');
- char *out = __sbrk (i);
-
- /* FIXME: In reality if the allocation fails, __sbrk will crash attempting to
- set the thread-local errno since the TCB has not yet been set up. This
- needs to be fixed with an __sbrk implementation that does not set
- errno. */
- if (out == (void *)-1)
- return NULL;
-
- i--;
-
- while (i-- > 0)
- out[i] = in[i];
-
- return out;
-}
-#endif
-
-static char **
-get_next_env (char **envp, char **name, size_t *namelen, char **val,
- char ***prev_envp)
-{
- while (envp != NULL && *envp != NULL)
- {
- char **prev = envp;
- char *envline = *envp++;
- int len = 0;
-
- while (envline[len] != '\0' && envline[len] != '=')
- len++;
-
- /* Just the name and no value, go to the next one. */
- if (envline[len] == '\0')
- continue;
-
- *name = envline;
- *namelen = len;
- *val = &envline[len + 1];
- *prev_envp = prev;
-
- return envp;
- }
-
- return NULL;
-}
-
-/* A stripped down strtoul-like implementation for very early use. It does not
- set errno if the result is outside bounds because it gets called before
- errno may have been set up. */
-static uint64_t
-tunables_strtoul (const char *nptr)
-{
- uint64_t result = 0;
- long int sign = 1;
- unsigned max_digit;
-
- while (*nptr == ' ' || *nptr == '\t')
- ++nptr;
-
- if (*nptr == '-')
- {
- sign = -1;
- ++nptr;
- }
- else if (*nptr == '+')
- ++nptr;
-
- if (*nptr < '0' || *nptr > '9')
- return 0UL;
-
- int base = 10;
- max_digit = 9;
- if (*nptr == '0')
- {
- if (nptr[1] == 'x' || nptr[1] == 'X')
- {
- base = 16;
- nptr += 2;
- }
- else
- {
- base = 8;
- max_digit = 7;
- }
- }
-
- while (1)
- {
- int digval;
- if (*nptr >= '0' && *nptr <= '0' + max_digit)
- digval = *nptr - '0';
- else if (base == 16)
- {
- if (*nptr >= 'a' && *nptr <= 'f')
- digval = *nptr - 'a' + 10;
- else if (*nptr >= 'A' && *nptr <= 'F')
- digval = *nptr - 'A' + 10;
- else
- break;
- }
- else
- break;
-
- if (result >= (UINT64_MAX - digval) / base)
- return UINT64_MAX;
- result *= base;
- result += digval;
- ++nptr;
- }
-
- return result * sign;
-}
-
-#define TUNABLE_SET_VAL_IF_VALID_RANGE(__cur, __val, __type, __default_min, \
- __default_max) \
-({ \
- __type min = (__cur)->type.min; \
- __type max = (__cur)->type.max; \
- \
- if (min == max) \
- { \
- min = __default_min; \
- max = __default_max; \
- } \
- \
- if ((__type) (__val) >= min && (__type) (val) <= max) \
- { \
- (__cur)->val.numval = val; \
- (__cur)->initialized = true; \
- } \
-})
-
-static void
-do_tunable_update_val (tunable_t *cur, const void *valp)
-{
- uint64_t val;
-
- if (cur->type.type_code != TUNABLE_TYPE_STRING)
- val = *((int64_t *) valp);
-
- switch (cur->type.type_code)
- {
- case TUNABLE_TYPE_INT_32:
- {
- TUNABLE_SET_VAL_IF_VALID_RANGE (cur, val, int64_t, INT32_MIN, INT32_MAX);
- break;
- }
- case TUNABLE_TYPE_UINT_64:
- {
- TUNABLE_SET_VAL_IF_VALID_RANGE (cur, val, uint64_t, 0, UINT64_MAX);
- break;
- }
- case TUNABLE_TYPE_SIZE_T:
- {
- TUNABLE_SET_VAL_IF_VALID_RANGE (cur, val, uint64_t, 0, SIZE_MAX);
- break;
- }
- case TUNABLE_TYPE_STRING:
- {
- cur->val.strval = valp;
- break;
- }
- default:
- __builtin_unreachable ();
- }
-}
-
-/* Validate range of the input value and initialize the tunable CUR if it looks
- good. */
-static void
-tunable_initialize (tunable_t *cur, const char *strval)
-{
- uint64_t val;
- const void *valp;
-
- if (cur->type.type_code != TUNABLE_TYPE_STRING)
- {
- val = tunables_strtoul (strval);
- valp = &val;
- }
- else
- {
- cur->initialized = true;
- valp = strval;
- }
- do_tunable_update_val (cur, valp);
-}
-
-void
-__tunable_set_val (tunable_id_t id, void *valp)
-{
- tunable_t *cur = &tunable_list[id];
-
- do_tunable_update_val (cur, valp);
-}
-
-#if TUNABLES_FRONTEND == TUNABLES_FRONTEND_valstring
-/* Parse the tunable string TUNESTR and adjust it to drop any tunables that may
- be unsafe for AT_SECURE processes so that it can be used as the new
- environment variable value for GLIBC_TUNABLES. VALSTRING is the original
- environment variable string which we use to make NULL terminated values so
- that we don't have to allocate memory again for it. */
-static void
-parse_tunables (char *tunestr, char *valstring)
-{
- if (tunestr == NULL || *tunestr == '\0')
- return;
-
- char *p = tunestr;
-
- while (true)
- {
- char *name = p;
- size_t len = 0;
-
- /* First, find where the name ends. */
- while (p[len] != '=' && p[len] != ':' && p[len] != '\0')
- len++;
-
- /* If we reach the end of the string before getting a valid name-value
- pair, bail out. */
- if (p[len] == '\0')
- return;
-
- /* We did not find a valid name-value pair before encountering the
- colon. */
- if (p[len]== ':')
- {
- p += len + 1;
- continue;
- }
-
- p += len + 1;
-
- /* Take the value from the valstring since we need to NULL terminate it. */
- char *value = &valstring[p - tunestr];
- len = 0;
-
- while (p[len] != ':' && p[len] != '\0')
- len++;
-
- /* Add the tunable if it exists. */
- for (size_t i = 0; i < sizeof (tunable_list) / sizeof (tunable_t); i++)
- {
- tunable_t *cur = &tunable_list[i];
-
- if (is_name (cur->name, name))
- {
- /* If we are in a secure context (AT_SECURE) then ignore the tunable
- unless it is explicitly marked as secure. Tunable values take
- precendence over their envvar aliases. */
- if (__libc_enable_secure)
- {
- if (cur->security_level == TUNABLE_SECLEVEL_SXID_ERASE)
- {
- if (p[len] == '\0')
- {
- /* Last tunable in the valstring. Null-terminate and
- return. */
- *name = '\0';
- return;
- }
- else
- {
- /* Remove the current tunable from the string. We do
- this by overwriting the string starting from NAME
- (which is where the current tunable begins) with
- the remainder of the string. We then have P point
- to NAME so that we continue in the correct
- position in the valstring. */
- char *q = &p[len + 1];
- p = name;
- while (*q != '\0')
- *name++ = *q++;
- name[0] = '\0';
- len = 0;
- }
- }
-
- if (cur->security_level != TUNABLE_SECLEVEL_NONE)
- break;
- }
-
- value[len] = '\0';
- tunable_initialize (cur, value);
- break;
- }
- }
-
- if (p[len] == '\0')
- return;
- else
- p += len + 1;
- }
-}
-#endif
-
-/* Enable the glibc.malloc.check tunable in SETUID/SETGID programs only when
- the system administrator has created the /etc/suid-debug file. This is a
- special case where we want to conditionally enable/disable a tunable even
- for setuid binaries. We use the special version of access() to avoid
- setting ERRNO, which is a TLS variable since TLS has not yet been set
- up. */
-static inline void
-__always_inline
-maybe_enable_malloc_check (void)
-{
- tunable_id_t id = TUNABLE_ENUM_NAME (glibc, malloc, check);
- if (__libc_enable_secure && __access_noerrno ("/etc/suid-debug", F_OK) == 0)
- tunable_list[id].security_level = TUNABLE_SECLEVEL_NONE;
-}
-
-/* Initialize the tunables list from the environment. For now we only use the
- ENV_ALIAS to find values. Later we will also use the tunable names to find
- values. */
-void
-__tunables_init (char **envp)
-{
- char *envname = NULL;
- char *envval = NULL;
- size_t len = 0;
- char **prev_envp = envp;
-
- maybe_enable_malloc_check ();
-
- while ((envp = get_next_env (envp, &envname, &len, &envval,
- &prev_envp)) != NULL)
- {
-#if TUNABLES_FRONTEND == TUNABLES_FRONTEND_valstring
- if (is_name (GLIBC_TUNABLES, envname))
- {
- char *new_env = tunables_strdup (envname);
- if (new_env != NULL)
- parse_tunables (new_env + len + 1, envval);
- /* Put in the updated envval. */
- *prev_envp = new_env;
- continue;
- }
-#endif
-
- for (int i = 0; i < sizeof (tunable_list) / sizeof (tunable_t); i++)
- {
- tunable_t *cur = &tunable_list[i];
-
- /* Skip over tunables that have either been set already or should be
- skipped. */
- if (cur->initialized || cur->env_alias == NULL)
- continue;
-
- const char *name = cur->env_alias;
-
- /* We have a match. Initialize and move on to the next line. */
- if (is_name (name, envname))
- {
- /* For AT_SECURE binaries, we need to check the security settings of
- the tunable and decide whether we read the value and also whether
- we erase the value so that child processes don't inherit them in
- the environment. */
- if (__libc_enable_secure)
- {
- if (cur->security_level == TUNABLE_SECLEVEL_SXID_ERASE)
- {
- /* Erase the environment variable. */
- char **ep = prev_envp;
-
- while (*ep != NULL)
- {
- if (is_name (name, *ep))
- {
- char **dp = ep;
-
- do
- dp[0] = dp[1];
- while (*dp++);
- }
- else
- ++ep;
- }
- /* Reset the iterator so that we read the environment again
- from the point we erased. */
- envp = prev_envp;
- }
-
- if (cur->security_level != TUNABLE_SECLEVEL_NONE)
- continue;
- }
-
- tunable_initialize (cur, envval);
- break;
- }
- }
- }
-}
-
-/* Set the tunable value. This is called by the module that the tunable exists
- in. */
-void
-__tunable_get_val (tunable_id_t id, void *valp, tunable_callback_t callback)
-{
- tunable_t *cur = &tunable_list[id];
-
- switch (cur->type.type_code)
- {
- case TUNABLE_TYPE_UINT_64:
- {
- *((uint64_t *) valp) = (uint64_t) cur->val.numval;
- break;
- }
- case TUNABLE_TYPE_INT_32:
- {
- *((int32_t *) valp) = (int32_t) cur->val.numval;
- break;
- }
- case TUNABLE_TYPE_SIZE_T:
- {
- *((size_t *) valp) = (size_t) cur->val.numval;
- break;
- }
- case TUNABLE_TYPE_STRING:
- {
- *((const char **)valp) = cur->val.strval;
- break;
- }
- default:
- __builtin_unreachable ();
- }
-
- if (cur->initialized && callback != NULL)
- callback (&cur->val);
-}
-
-rtld_hidden_def (__tunable_get_val)
diff --git a/elf/dl-tunables.h b/elf/dl-tunables.h
deleted file mode 100644
index 6c49dcbf47..0000000000
--- a/elf/dl-tunables.h
+++ /dev/null
@@ -1,115 +0,0 @@
-/* The tunable framework. See the README to know how to use the tunable in
- a glibc module.
-
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _TUNABLES_H_
-#define _TUNABLES_H_
-
-#if !HAVE_TUNABLES
-static inline void
-__always_inline
-__tunables_init (char **unused __attribute__ ((unused)))
-{
- /* This is optimized out if tunables are not enabled. */
-}
-#else
-
-# include <stddef.h>
-# include "dl-tunable-types.h"
-
-/* A tunable. */
-struct _tunable
-{
- const char *name; /* Internal name of the tunable. */
- tunable_type_t type; /* Data type of the tunable. */
- tunable_val_t val; /* The value. */
- bool initialized; /* Flag to indicate that the tunable is
- initialized. */
- tunable_seclevel_t security_level; /* Specify the security level for the
- tunable with respect to AT_SECURE
- programs. See description of
- tunable_seclevel_t to see a
- description of the values.
-
- Note that even if the tunable is
- read, it may not get used by the
- target module if the value is
- considered unsafe. */
- /* Compatibility elements. */
- const char *env_alias; /* The compatibility environment
- variable name. */
-};
-
-typedef struct _tunable tunable_t;
-
-/* Full name for a tunable is top_ns.tunable_ns.id. */
-# define TUNABLE_NAME_S(top,ns,id) #top "." #ns "." #id
-
-# define TUNABLE_ENUM_NAME(__top,__ns,__id) TUNABLE_ENUM_NAME1 (__top,__ns,__id)
-# define TUNABLE_ENUM_NAME1(__top,__ns,__id) __top ## _ ## __ns ## _ ## __id
-
-# include "dl-tunable-list.h"
-
-extern void __tunables_init (char **);
-extern void __tunable_get_val (tunable_id_t, void *, tunable_callback_t);
-extern void __tunable_set_val (tunable_id_t, void *);
-rtld_hidden_proto (__tunables_init)
-rtld_hidden_proto (__tunable_get_val)
-
-/* Define TUNABLE_GET and TUNABLE_SET in short form if TOP_NAMESPACE and
- TUNABLE_NAMESPACE are defined. This is useful shorthand to get and set
- tunables within a module. */
-#if defined TOP_NAMESPACE && defined TUNABLE_NAMESPACE
-# define TUNABLE_GET(__id, __type, __cb) \
- TUNABLE_GET_FULL (TOP_NAMESPACE, TUNABLE_NAMESPACE, __id, __type, __cb)
-# define TUNABLE_SET(__id, __type, __val) \
- TUNABLE_SET_FULL (TOP_NAMESPACE, TUNABLE_NAMESPACE, __id, __type, __val)
-#else
-# define TUNABLE_GET(__top, __ns, __id, __type, __cb) \
- TUNABLE_GET_FULL (__top, __ns, __id, __type, __cb)
-# define TUNABLE_SET(__top, __ns, __id, __type, __val) \
- TUNABLE_SET_FULL (__top, __ns, __id, __type, __val)
-#endif
-
-/* Get and return a tunable value. If the tunable was set externally and __CB
- is defined then call __CB before returning the value. */
-# define TUNABLE_GET_FULL(__top, __ns, __id, __type, __cb) \
-({ \
- tunable_id_t id = TUNABLE_ENUM_NAME (__top, __ns, __id); \
- __type ret; \
- __tunable_get_val (id, &ret, __cb); \
- ret; \
-})
-
-/* Set a tunable value. */
-# define TUNABLE_SET_FULL(__top, __ns, __id, __type, __val) \
-({ \
- __tunable_set_val (TUNABLE_ENUM_NAME (__top, __ns, __id), \
- & (__type) {__val}); \
-})
-
-/* Namespace sanity for callback functions. Use this macro to keep the
- namespace of the modules clean. */
-# define TUNABLE_CALLBACK(__name) _dl_tunable_ ## __name
-
-# define TUNABLES_FRONTEND_valstring 1
-/* The default value for TUNABLES_FRONTEND. */
-# define TUNABLES_FRONTEND_yes TUNABLES_FRONTEND_valstring
-#endif
-#endif
diff --git a/elf/dl-tunables.list b/elf/dl-tunables.list
deleted file mode 100644
index 41ce9afa28..0000000000
--- a/elf/dl-tunables.list
+++ /dev/null
@@ -1,87 +0,0 @@
-# Copyright (C) 2016-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-# Allowed attributes for tunables:
-#
-# type: Defaults to STRING
-# minval: Optional minimum acceptable value
-# maxval: Optional maximum acceptable value
-# env_alias: An alias environment variable
-# security_level: Specify security level of the tunable. Valid values are:
-#
-# SXID_ERASE: (default) Don't read for AT_SECURE binaries and
-# removed so that child processes can't read it.
-# SXID_IGNORE: Don't read for AT_SECURE binaries, but retained for
-# non-AT_SECURE subprocesses.
-# NONE: Read all the time.
-
-glibc {
- malloc {
- check {
- type: INT_32
- minval: 0
- maxval: 3
- env_alias: MALLOC_CHECK_
- }
- top_pad {
- type: SIZE_T
- env_alias: MALLOC_TOP_PAD_
- security_level: SXID_IGNORE
- }
- perturb {
- type: INT_32
- minval: 0
- maxval: 0xff
- env_alias: MALLOC_PERTURB_
- security_level: SXID_IGNORE
- }
- mmap_threshold {
- type: SIZE_T
- env_alias: MALLOC_MMAP_THRESHOLD_
- security_level: SXID_IGNORE
- }
- trim_threshold {
- type: SIZE_T
- env_alias: MALLOC_TRIM_THRESHOLD_
- security_level: SXID_IGNORE
- }
- mmap_max {
- type: INT_32
- env_alias: MALLOC_MMAP_MAX_
- security_level: SXID_IGNORE
- }
- arena_max {
- type: SIZE_T
- env_alias: MALLOC_ARENA_MAX
- minval: 1
- security_level: SXID_IGNORE
- }
- arena_test {
- type: SIZE_T
- env_alias: MALLOC_ARENA_TEST
- minval: 1
- security_level: SXID_IGNORE
- }
- }
- tune {
- hwcap_mask {
- type: UINT_64
- env_alias: LD_HWCAP_MASK
- default: HWCAP_IMPORTANT
- }
- }
-}
diff --git a/elf/dl-unmap-segments.h b/elf/dl-unmap-segments.h
deleted file mode 100644
index f37e183943..0000000000
--- a/elf/dl-unmap-segments.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Unmap a shared object's segments. Generic version.
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _DL_UNMAP_SEGMENTS_H
-#define _DL_UNMAP_SEGMENTS_H 1
-
-#include <link.h>
-#include <sys/mman.h>
-
-/* _dl_map_segments ensures that any whole pages in gaps between segments
- are filled in with PROT_NONE mappings. So we can just unmap the whole
- range in one fell swoop. */
-
-static __always_inline void
-_dl_unmap_segments (struct link_map *l)
-{
- __munmap ((void *) l->l_map_start, l->l_map_end - l->l_map_start);
-}
-
-#endif /* dl-unmap-segments.h */
diff --git a/elf/dl-version.c b/elf/dl-version.c
deleted file mode 100644
index c00078e5e4..0000000000
--- a/elf/dl-version.c
+++ /dev/null
@@ -1,389 +0,0 @@
-/* Handle symbol and library versioning.
- Copyright (C) 1997-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <elf.h>
-#include <errno.h>
-#include <libintl.h>
-#include <stdlib.h>
-#include <string.h>
-#include <ldsodefs.h>
-#include <_itoa.h>
-
-#include <assert.h>
-
-
-#define make_string(string, rest...) \
- ({ \
- const char *all[] = { string, ## rest }; \
- size_t len, cnt; \
- char *result, *cp; \
- \
- len = 1; \
- for (cnt = 0; cnt < sizeof (all) / sizeof (all[0]); ++cnt) \
- len += strlen (all[cnt]); \
- \
- cp = result = alloca (len); \
- for (cnt = 0; cnt < sizeof (all) / sizeof (all[0]); ++cnt) \
- cp = __stpcpy (cp, all[cnt]); \
- \
- result; \
- })
-
-
-static inline struct link_map *
-__attribute ((always_inline))
-find_needed (const char *name, struct link_map *map)
-{
- struct link_map *tmap;
- unsigned int n;
-
- for (tmap = GL(dl_ns)[map->l_ns]._ns_loaded; tmap != NULL;
- tmap = tmap->l_next)
- if (_dl_name_match_p (name, tmap))
- return tmap;
-
- /* The required object is not in the global scope, look to see if it is
- a dependency of the current object. */
- for (n = 0; n < map->l_searchlist.r_nlist; n++)
- if (_dl_name_match_p (name, map->l_searchlist.r_list[n]))
- return map->l_searchlist.r_list[n];
-
- /* Should never happen. */
- return NULL;
-}
-
-
-static int
-internal_function
-match_symbol (const char *name, Lmid_t ns, ElfW(Word) hash, const char *string,
- struct link_map *map, int verbose, int weak)
-{
- const char *strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
- ElfW(Addr) def_offset;
- ElfW(Verdef) *def;
- /* Initialize to make the compiler happy. */
- const char *errstring = NULL;
- int result = 0;
-
- /* Display information about what we are doing while debugging. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_VERSIONS))
- _dl_debug_printf ("\
-checking for version `%s' in file %s [%lu] required by file %s [%lu]\n",
- string, DSO_FILENAME (map->l_name),
- map->l_ns, name, ns);
-
- if (__glibc_unlikely (map->l_info[VERSYMIDX (DT_VERDEF)] == NULL))
- {
- /* The file has no symbol versioning. I.e., the dependent
- object was linked against another version of this file. We
- only print a message if verbose output is requested. */
- if (verbose)
- {
- /* XXX We cannot translate the messages. */
- errstring = make_string ("\
-no version information available (required by ", name, ")");
- goto call_cerror;
- }
- return 0;
- }
-
- def_offset = map->l_info[VERSYMIDX (DT_VERDEF)]->d_un.d_ptr;
- assert (def_offset != 0);
-
- def = (ElfW(Verdef) *) ((char *) map->l_addr + def_offset);
- while (1)
- {
- /* Currently the version number of the definition entry is 1.
- Make sure all we see is this version. */
- if (__builtin_expect (def->vd_version, 1) != 1)
- {
- char buf[20];
- buf[sizeof (buf) - 1] = '\0';
- /* XXX We cannot translate the message. */
- errstring = make_string ("unsupported version ",
- _itoa (def->vd_version,
- &buf[sizeof (buf) - 1], 10, 0),
- " of Verdef record");
- result = 1;
- goto call_cerror;
- }
-
- /* Compare the hash values. */
- if (hash == def->vd_hash)
- {
- ElfW(Verdaux) *aux = (ElfW(Verdaux) *) ((char *) def + def->vd_aux);
-
- /* To be safe, compare the string as well. */
- if (__builtin_expect (strcmp (string, strtab + aux->vda_name), 0)
- == 0)
- /* Bingo! */
- return 0;
- }
-
- /* If no more definitions we failed to find what we want. */
- if (def->vd_next == 0)
- break;
-
- /* Next definition. */
- def = (ElfW(Verdef) *) ((char *) def + def->vd_next);
- }
-
- /* Symbol not found. If it was a weak reference it is not fatal. */
- if (__glibc_likely (weak))
- {
- if (verbose)
- {
- /* XXX We cannot translate the message. */
- errstring = make_string ("weak version `", string,
- "' not found (required by ", name, ")");
- goto call_cerror;
- }
- return 0;
- }
-
- /* XXX We cannot translate the message. */
- errstring = make_string ("version `", string, "' not found (required by ",
- name, ")");
- result = 1;
- call_cerror:
- _dl_signal_cerror (0, DSO_FILENAME (map->l_name),
- N_("version lookup error"), errstring);
- return result;
-}
-
-
-int
-internal_function
-_dl_check_map_versions (struct link_map *map, int verbose, int trace_mode)
-{
- int result = 0;
- const char *strtab;
- /* Pointer to section with needed versions. */
- ElfW(Dyn) *dyn;
- /* Pointer to dynamic section with definitions. */
- ElfW(Dyn) *def;
- /* We need to find out which is the highest version index used
- in a dependecy. */
- unsigned int ndx_high = 0;
- /* Initialize to make the compiler happy. */
- const char *errstring = NULL;
- int errval = 0;
-
- /* If we don't have a string table, we must be ok. */
- if (map->l_info[DT_STRTAB] == NULL)
- return 0;
- strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
-
- dyn = map->l_info[VERSYMIDX (DT_VERNEED)];
- def = map->l_info[VERSYMIDX (DT_VERDEF)];
-
- if (dyn != NULL)
- {
- /* This file requires special versions from its dependencies. */
- ElfW(Verneed) *ent = (ElfW(Verneed) *) (map->l_addr + dyn->d_un.d_ptr);
-
- /* Currently the version number of the needed entry is 1.
- Make sure all we see is this version. */
- if (__builtin_expect (ent->vn_version, 1) != 1)
- {
- char buf[20];
- buf[sizeof (buf) - 1] = '\0';
- /* XXX We cannot translate the message. */
- errstring = make_string ("unsupported version ",
- _itoa (ent->vn_version,
- &buf[sizeof (buf) - 1], 10, 0),
- " of Verneed record\n");
- call_error:
- _dl_signal_error (errval, DSO_FILENAME (map->l_name),
- NULL, errstring);
- }
-
- while (1)
- {
- ElfW(Vernaux) *aux;
- struct link_map *needed = find_needed (strtab + ent->vn_file, map);
-
- /* If NEEDED is NULL this means a dependency was not found
- and no stub entry was created. This should never happen. */
- assert (needed != NULL);
-
- /* Make sure this is no stub we created because of a missing
- dependency. */
- if (__builtin_expect (! trace_mode, 1)
- || ! __builtin_expect (needed->l_faked, 0))
- {
- /* NEEDED is the map for the file we need. Now look for the
- dependency symbols. */
- aux = (ElfW(Vernaux) *) ((char *) ent + ent->vn_aux);
- while (1)
- {
- /* Match the symbol. */
- result |= match_symbol (DSO_FILENAME (map->l_name),
- map->l_ns, aux->vna_hash,
- strtab + aux->vna_name,
- needed->l_real, verbose,
- aux->vna_flags & VER_FLG_WEAK);
-
- /* Compare the version index. */
- if ((unsigned int) (aux->vna_other & 0x7fff) > ndx_high)
- ndx_high = aux->vna_other & 0x7fff;
-
- if (aux->vna_next == 0)
- /* No more symbols. */
- break;
-
- /* Next symbol. */
- aux = (ElfW(Vernaux) *) ((char *) aux + aux->vna_next);
- }
- }
-
- if (ent->vn_next == 0)
- /* No more dependencies. */
- break;
-
- /* Next dependency. */
- ent = (ElfW(Verneed) *) ((char *) ent + ent->vn_next);
- }
- }
-
- /* We also must store the names of the defined versions. Determine
- the maximum index here as well.
-
- XXX We could avoid the loop by just taking the number of definitions
- as an upper bound of new indeces. */
- if (def != NULL)
- {
- ElfW(Verdef) *ent;
- ent = (ElfW(Verdef) *) (map->l_addr + def->d_un.d_ptr);
- while (1)
- {
- if ((unsigned int) (ent->vd_ndx & 0x7fff) > ndx_high)
- ndx_high = ent->vd_ndx & 0x7fff;
-
- if (ent->vd_next == 0)
- /* No more definitions. */
- break;
-
- ent = (ElfW(Verdef) *) ((char *) ent + ent->vd_next);
- }
- }
-
- if (ndx_high > 0)
- {
- /* Now we are ready to build the array with the version names
- which can be indexed by the version index in the VERSYM
- section. */
- map->l_versions = (struct r_found_version *)
- calloc (ndx_high + 1, sizeof (*map->l_versions));
- if (__glibc_unlikely (map->l_versions == NULL))
- {
- errstring = N_("cannot allocate version reference table");
- errval = ENOMEM;
- goto call_error;
- }
-
- /* Store the number of available symbols. */
- map->l_nversions = ndx_high + 1;
-
- /* Compute the pointer to the version symbols. */
- map->l_versyms = (void *) D_PTR (map, l_info[VERSYMIDX (DT_VERSYM)]);
-
- if (dyn != NULL)
- {
- ElfW(Verneed) *ent;
- ent = (ElfW(Verneed) *) (map->l_addr + dyn->d_un.d_ptr);
- while (1)
- {
- ElfW(Vernaux) *aux;
- aux = (ElfW(Vernaux) *) ((char *) ent + ent->vn_aux);
- while (1)
- {
- ElfW(Half) ndx = aux->vna_other & 0x7fff;
- /* In trace mode, dependencies may be missing. */
- if (__glibc_likely (ndx < map->l_nversions))
- {
- map->l_versions[ndx].hash = aux->vna_hash;
- map->l_versions[ndx].hidden = aux->vna_other & 0x8000;
- map->l_versions[ndx].name = &strtab[aux->vna_name];
- map->l_versions[ndx].filename = &strtab[ent->vn_file];
- }
-
- if (aux->vna_next == 0)
- /* No more symbols. */
- break;
-
- /* Advance to next symbol. */
- aux = (ElfW(Vernaux) *) ((char *) aux + aux->vna_next);
- }
-
- if (ent->vn_next == 0)
- /* No more dependencies. */
- break;
-
- /* Advance to next dependency. */
- ent = (ElfW(Verneed) *) ((char *) ent + ent->vn_next);
- }
- }
-
- /* And insert the defined versions. */
- if (def != NULL)
- {
- ElfW(Verdef) *ent;
- ent = (ElfW(Verdef) *) (map->l_addr + def->d_un.d_ptr);
- while (1)
- {
- ElfW(Verdaux) *aux;
- aux = (ElfW(Verdaux) *) ((char *) ent + ent->vd_aux);
-
- if ((ent->vd_flags & VER_FLG_BASE) == 0)
- {
- /* The name of the base version should not be
- available for matching a versioned symbol. */
- ElfW(Half) ndx = ent->vd_ndx & 0x7fff;
- map->l_versions[ndx].hash = ent->vd_hash;
- map->l_versions[ndx].name = &strtab[aux->vda_name];
- map->l_versions[ndx].filename = NULL;
- }
-
- if (ent->vd_next == 0)
- /* No more definitions. */
- break;
-
- ent = (ElfW(Verdef) *) ((char *) ent + ent->vd_next);
- }
- }
- }
-
- return result;
-}
-
-
-int
-internal_function
-_dl_check_all_versions (struct link_map *map, int verbose, int trace_mode)
-{
- struct link_map *l;
- int result = 0;
-
- for (l = map; l != NULL; l = l->l_next)
- result |= (! l->l_faked
- && _dl_check_map_versions (l, verbose, trace_mode));
-
- return result;
-}
diff --git a/elf/dl-writev.h b/elf/dl-writev.h
deleted file mode 100644
index 4db083bef6..0000000000
--- a/elf/dl-writev.h
+++ /dev/null
@@ -1,56 +0,0 @@
-/* Message-writing for the dynamic linker. Generic version.
- Copyright (C) 2013-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <sys/uio.h>
-#include <ldsodefs.h>
-#include <libc-lock.h>
-
-/* This is used from only one place: dl-misc.c:_dl_debug_vdprintf.
- Hence it's in a header with the expectation it will be inlined.
-
- This is writev, but with a constraint added and others loosened:
-
- 1. Under RTLD_PRIVATE_ERRNO, it must not clobber the private errno
- when another thread holds the dl_load_lock.
- 2. It is not obliged to detect and report errors at all.
- 3. It's not really obliged to deliver a single atomic write
- (though it may be preferable). */
-
-static inline void
-_dl_writev (int fd, const struct iovec *iov, size_t niov)
-{
- /* Note that if __writev is an implementation that calls malloc,
- this will cause linking problems building the dynamic linker. */
-
-#if RTLD_PRIVATE_ERRNO
- /* We have to take this lock just to be sure we don't clobber the private
- errno when it's being used by another thread that cares about it.
- Yet we must be sure not to try calling the lock functions before
- the thread library is fully initialized. */
- if (__glibc_unlikely (_dl_starting_up))
- __writev (fd, iov, niov);
- else
- {
- __rtld_lock_lock_recursive (GL(dl_load_lock));
- __writev (fd, iov, niov);
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- }
-#else
- __writev (fd, iov, niov);
-#endif
-}
diff --git a/elf/do-rel.h b/elf/do-rel.h
deleted file mode 100644
index 70071e5c44..0000000000
--- a/elf/do-rel.h
+++ /dev/null
@@ -1,191 +0,0 @@
-/* Do relocations for ELF dynamic linking.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file may be included twice, to define both
- `elf_dynamic_do_rel' and `elf_dynamic_do_rela'. */
-
-#ifdef DO_RELA
-# define elf_dynamic_do_Rel elf_dynamic_do_Rela
-# define Rel Rela
-# define elf_machine_rel elf_machine_rela
-# define elf_machine_rel_relative elf_machine_rela_relative
-#endif
-
-#ifndef DO_ELF_MACHINE_REL_RELATIVE
-# define DO_ELF_MACHINE_REL_RELATIVE(map, l_addr, relative) \
- elf_machine_rel_relative (l_addr, relative, \
- (void *) (l_addr + relative->r_offset))
-#endif
-
-/* Perform the relocations in MAP on the running program image as specified
- by RELTAG, SZTAG. If LAZY is nonzero, this is the first pass on PLT
- relocations; they should be set up to call _dl_runtime_resolve, rather
- than fully resolved now. */
-
-auto inline void __attribute__ ((always_inline))
-elf_dynamic_do_Rel (struct link_map *map,
- ElfW(Addr) reladdr, ElfW(Addr) relsize,
- __typeof (((ElfW(Dyn) *) 0)->d_un.d_val) nrelative,
- int lazy, int skip_ifunc)
-{
- const ElfW(Rel) *r = (const void *) reladdr;
- const ElfW(Rel) *end = (const void *) (reladdr + relsize);
- ElfW(Addr) l_addr = map->l_addr;
-# if defined ELF_MACHINE_IRELATIVE && !defined RTLD_BOOTSTRAP
- const ElfW(Rel) *r2 = NULL;
- const ElfW(Rel) *end2 = NULL;
-# endif
-
-#if (!defined DO_RELA || !defined ELF_MACHINE_PLT_REL) && !defined RTLD_BOOTSTRAP
- /* We never bind lazily during ld.so bootstrap. Unfortunately gcc is
- not clever enough to see through all the function calls to realize
- that. */
- if (lazy)
- {
- /* Doing lazy PLT relocations; they need very little info. */
- for (; r < end; ++r)
-# ifdef ELF_MACHINE_IRELATIVE
- if (ELFW(R_TYPE) (r->r_info) == ELF_MACHINE_IRELATIVE)
- {
- if (r2 == NULL)
- r2 = r;
- end2 = r;
- }
- else
-# endif
- elf_machine_lazy_rel (map, l_addr, r, skip_ifunc);
-
-# ifdef ELF_MACHINE_IRELATIVE
- if (r2 != NULL)
- for (; r2 <= end2; ++r2)
- if (ELFW(R_TYPE) (r2->r_info) == ELF_MACHINE_IRELATIVE)
- elf_machine_lazy_rel (map, l_addr, r2, skip_ifunc);
-# endif
- }
- else
-#endif
- {
- const ElfW(Sym) *const symtab =
- (const void *) D_PTR (map, l_info[DT_SYMTAB]);
- const ElfW(Rel) *relative = r;
- r += nrelative;
-
-#ifndef RTLD_BOOTSTRAP
- /* This is defined in rtld.c, but nowhere in the static libc.a; make
- the reference weak so static programs can still link. This
- declaration cannot be done when compiling rtld.c (i.e. #ifdef
- RTLD_BOOTSTRAP) because rtld.c contains the common defn for
- _dl_rtld_map, which is incompatible with a weak decl in the same
- file. */
-# ifndef SHARED
- weak_extern (GL(dl_rtld_map));
-# endif
- if (map != &GL(dl_rtld_map)) /* Already done in rtld itself. */
-# if !defined DO_RELA || defined ELF_MACHINE_REL_RELATIVE
- /* Rela platforms get the offset from r_addend and this must
- be copied in the relocation address. Therefore we can skip
- the relative relocations only if this is for rel
- relocations or rela relocations if they are computed as
- memory_loc += l_addr... */
- if (l_addr != 0)
-# else
- /* ...or we know the object has been prelinked. */
- if (l_addr != 0 || ! map->l_info[VALIDX(DT_GNU_PRELINKED)])
-# endif
-#endif
- for (; relative < r; ++relative)
- DO_ELF_MACHINE_REL_RELATIVE (map, l_addr, relative);
-
-#ifdef RTLD_BOOTSTRAP
- /* The dynamic linker always uses versioning. */
- assert (map->l_info[VERSYMIDX (DT_VERSYM)] != NULL);
-#else
- if (map->l_info[VERSYMIDX (DT_VERSYM)])
-#endif
- {
- const ElfW(Half) *const version =
- (const void *) D_PTR (map, l_info[VERSYMIDX (DT_VERSYM)]);
-
- for (; r < end; ++r)
- {
-#if defined ELF_MACHINE_IRELATIVE && !defined RTLD_BOOTSTRAP
- if (ELFW(R_TYPE) (r->r_info) == ELF_MACHINE_IRELATIVE)
- {
- if (r2 == NULL)
- r2 = r;
- end2 = r;
- continue;
- }
-#endif
-
- ElfW(Half) ndx = version[ELFW(R_SYM) (r->r_info)] & 0x7fff;
- elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)],
- &map->l_versions[ndx],
- (void *) (l_addr + r->r_offset), skip_ifunc);
- }
-
-#if defined ELF_MACHINE_IRELATIVE && !defined RTLD_BOOTSTRAP
- if (r2 != NULL)
- for (; r2 <= end2; ++r2)
- if (ELFW(R_TYPE) (r2->r_info) == ELF_MACHINE_IRELATIVE)
- {
- ElfW(Half) ndx
- = version[ELFW(R_SYM) (r2->r_info)] & 0x7fff;
- elf_machine_rel (map, r2,
- &symtab[ELFW(R_SYM) (r2->r_info)],
- &map->l_versions[ndx],
- (void *) (l_addr + r2->r_offset),
- skip_ifunc);
- }
-#endif
- }
-#ifndef RTLD_BOOTSTRAP
- else
- {
- for (; r < end; ++r)
-# ifdef ELF_MACHINE_IRELATIVE
- if (ELFW(R_TYPE) (r->r_info) == ELF_MACHINE_IRELATIVE)
- {
- if (r2 == NULL)
- r2 = r;
- end2 = r;
- }
- else
-# endif
- elf_machine_rel (map, r, &symtab[ELFW(R_SYM) (r->r_info)], NULL,
- (void *) (l_addr + r->r_offset), skip_ifunc);
-
-# ifdef ELF_MACHINE_IRELATIVE
- if (r2 != NULL)
- for (; r2 <= end2; ++r2)
- if (ELFW(R_TYPE) (r2->r_info) == ELF_MACHINE_IRELATIVE)
- elf_machine_rel (map, r2, &symtab[ELFW(R_SYM) (r2->r_info)],
- NULL, (void *) (l_addr + r2->r_offset),
- skip_ifunc);
-# endif
- }
-#endif
- }
-}
-
-#undef elf_dynamic_do_Rel
-#undef Rel
-#undef elf_machine_rel
-#undef elf_machine_rel_relative
-#undef DO_ELF_MACHINE_REL_RELATIVE
-#undef DO_RELA
diff --git a/elf/dynamic-link.h b/elf/dynamic-link.h
deleted file mode 100644
index 60f2d91151..0000000000
--- a/elf/dynamic-link.h
+++ /dev/null
@@ -1,203 +0,0 @@
-/* Inline functions for dynamic linking.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This macro is used as a callback from elf_machine_rel{a,} when a
- static TLS reloc is about to be performed. Since (in dl-load.c) we
- permit dynamic loading of objects that might use such relocs, we
- have to check whether each use is actually doable. If the object
- whose TLS segment the reference resolves to was allocated space in
- the static TLS block at startup, then it's ok. Otherwise, we make
- an attempt to allocate it in surplus space on the fly. If that
- can't be done, we fall back to the error that DF_STATIC_TLS is
- intended to produce. */
-#define HAVE_STATIC_TLS(map, sym_map) \
- (__builtin_expect ((sym_map)->l_tls_offset != NO_TLS_OFFSET \
- && ((sym_map)->l_tls_offset \
- != FORCED_DYNAMIC_TLS_OFFSET), 1))
-
-#define CHECK_STATIC_TLS(map, sym_map) \
- do { \
- if (!HAVE_STATIC_TLS (map, sym_map)) \
- _dl_allocate_static_tls (sym_map); \
- } while (0)
-
-#define TRY_STATIC_TLS(map, sym_map) \
- (__builtin_expect ((sym_map)->l_tls_offset \
- != FORCED_DYNAMIC_TLS_OFFSET, 1) \
- && (__builtin_expect ((sym_map)->l_tls_offset != NO_TLS_OFFSET, 1) \
- || _dl_try_allocate_static_tls (sym_map) == 0))
-
-int internal_function attribute_hidden
- _dl_try_allocate_static_tls (struct link_map *map);
-
-#include <elf.h>
-
-#ifdef RESOLVE_MAP
-/* We pass reloc_addr as a pointer to void, as opposed to a pointer to
- ElfW(Addr), because not all architectures can assume that the
- relocated address is properly aligned, whereas the compiler is
- entitled to assume that a pointer to a type is properly aligned for
- the type. Even if we cast the pointer back to some other type with
- less strict alignment requirements, the compiler might still
- remember that the pointer was originally more aligned, thereby
- optimizing away alignment tests or using word instructions for
- copying memory, breaking the very code written to handle the
- unaligned cases. */
-# if ! ELF_MACHINE_NO_REL
-auto inline void __attribute__((always_inline))
-elf_machine_rel (struct link_map *map, const ElfW(Rel) *reloc,
- const ElfW(Sym) *sym, const struct r_found_version *version,
- void *const reloc_addr, int skip_ifunc);
-auto inline void __attribute__((always_inline))
-elf_machine_rel_relative (ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
- void *const reloc_addr);
-# endif
-# if ! ELF_MACHINE_NO_RELA
-auto inline void __attribute__((always_inline))
-elf_machine_rela (struct link_map *map, const ElfW(Rela) *reloc,
- const ElfW(Sym) *sym, const struct r_found_version *version,
- void *const reloc_addr, int skip_ifunc);
-auto inline void __attribute__((always_inline))
-elf_machine_rela_relative (ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
- void *const reloc_addr);
-# endif
-# if ELF_MACHINE_NO_RELA || defined ELF_MACHINE_PLT_REL
-auto inline void __attribute__((always_inline))
-elf_machine_lazy_rel (struct link_map *map,
- ElfW(Addr) l_addr, const ElfW(Rel) *reloc,
- int skip_ifunc);
-# else
-auto inline void __attribute__((always_inline))
-elf_machine_lazy_rel (struct link_map *map,
- ElfW(Addr) l_addr, const ElfW(Rela) *reloc,
- int skip_ifunc);
-# endif
-#endif
-
-#include <dl-machine.h>
-
-#include "get-dynamic-info.h"
-
-#ifdef RESOLVE_MAP
-
-# ifdef RTLD_BOOTSTRAP
-# define ELF_DURING_STARTUP (1)
-# else
-# define ELF_DURING_STARTUP (0)
-# endif
-
-/* Get the definitions of `elf_dynamic_do_rel' and `elf_dynamic_do_rela'.
- These functions are almost identical, so we use cpp magic to avoid
- duplicating their code. It cannot be done in a more general function
- because we must be able to completely inline. */
-
-/* On some machines, notably SPARC, DT_REL* includes DT_JMPREL in its
- range. Note that according to the ELF spec, this is completely legal!
-
- We are guarenteed that we have one of three situations. Either DT_JMPREL
- comes immediately after DT_REL*, or there is overlap and DT_JMPREL
- consumes precisely the very end of the DT_REL*, or DT_JMPREL and DT_REL*
- are completely separate and there is a gap between them. */
-
-# define _ELF_DYNAMIC_DO_RELOC(RELOC, reloc, map, do_lazy, skip_ifunc, test_rel) \
- do { \
- struct { ElfW(Addr) start, size; \
- __typeof (((ElfW(Dyn) *) 0)->d_un.d_val) nrelative; int lazy; } \
- ranges[2] = { { 0, 0, 0, 0 }, { 0, 0, 0, 0 } }; \
- \
- if ((map)->l_info[DT_##RELOC]) \
- { \
- ranges[0].start = D_PTR ((map), l_info[DT_##RELOC]); \
- ranges[0].size = (map)->l_info[DT_##RELOC##SZ]->d_un.d_val; \
- if (map->l_info[VERSYMIDX (DT_##RELOC##COUNT)] != NULL) \
- ranges[0].nrelative \
- = map->l_info[VERSYMIDX (DT_##RELOC##COUNT)]->d_un.d_val; \
- } \
- if ((map)->l_info[DT_PLTREL] \
- && (!test_rel || (map)->l_info[DT_PLTREL]->d_un.d_val == DT_##RELOC)) \
- { \
- ElfW(Addr) start = D_PTR ((map), l_info[DT_JMPREL]); \
- ElfW(Addr) size = (map)->l_info[DT_PLTRELSZ]->d_un.d_val; \
- \
- if (ranges[0].start + ranges[0].size == (start + size)) \
- ranges[0].size -= size; \
- if (ELF_DURING_STARTUP \
- || (!(do_lazy) \
- && (ranges[0].start + ranges[0].size) == start)) \
- { \
- /* Combine processing the sections. */ \
- ranges[0].size += size; \
- } \
- else \
- { \
- ranges[1].start = start; \
- ranges[1].size = size; \
- ranges[1].lazy = (do_lazy); \
- } \
- } \
- \
- if (ELF_DURING_STARTUP) \
- elf_dynamic_do_##reloc ((map), ranges[0].start, ranges[0].size, \
- ranges[0].nrelative, 0, skip_ifunc); \
- else \
- { \
- int ranges_index; \
- for (ranges_index = 0; ranges_index < 2; ++ranges_index) \
- elf_dynamic_do_##reloc ((map), \
- ranges[ranges_index].start, \
- ranges[ranges_index].size, \
- ranges[ranges_index].nrelative, \
- ranges[ranges_index].lazy, \
- skip_ifunc); \
- } \
- } while (0)
-
-# if ELF_MACHINE_NO_REL || ELF_MACHINE_NO_RELA
-# define _ELF_CHECK_REL 0
-# else
-# define _ELF_CHECK_REL 1
-# endif
-
-# if ! ELF_MACHINE_NO_REL
-# include "do-rel.h"
-# define ELF_DYNAMIC_DO_REL(map, lazy, skip_ifunc) \
- _ELF_DYNAMIC_DO_RELOC (REL, Rel, map, lazy, skip_ifunc, _ELF_CHECK_REL)
-# else
-# define ELF_DYNAMIC_DO_REL(map, lazy, skip_ifunc) /* Nothing to do. */
-# endif
-
-# if ! ELF_MACHINE_NO_RELA
-# define DO_RELA
-# include "do-rel.h"
-# define ELF_DYNAMIC_DO_RELA(map, lazy, skip_ifunc) \
- _ELF_DYNAMIC_DO_RELOC (RELA, Rela, map, lazy, skip_ifunc, _ELF_CHECK_REL)
-# else
-# define ELF_DYNAMIC_DO_RELA(map, lazy, skip_ifunc) /* Nothing to do. */
-# endif
-
-/* This can't just be an inline function because GCC is too dumb
- to inline functions containing inlines themselves. */
-# define ELF_DYNAMIC_RELOCATE(map, lazy, consider_profile, skip_ifunc) \
- do { \
- int edr_lazy = elf_machine_runtime_setup ((map), (lazy), \
- (consider_profile)); \
- ELF_DYNAMIC_DO_REL ((map), edr_lazy, skip_ifunc); \
- ELF_DYNAMIC_DO_RELA ((map), edr_lazy, skip_ifunc); \
- } while (0)
-
-#endif
diff --git a/elf/elf.h b/elf/elf.h
deleted file mode 100644
index fff893d433..0000000000
--- a/elf/elf.h
+++ /dev/null
@@ -1,3761 +0,0 @@
-/* This file defines standard ELF types, structures, and macros.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _ELF_H
-#define _ELF_H 1
-
-#include <features.h>
-
-__BEGIN_DECLS
-
-/* Standard ELF types. */
-
-#include <stdint.h>
-
-/* Type for a 16-bit quantity. */
-typedef uint16_t Elf32_Half;
-typedef uint16_t Elf64_Half;
-
-/* Types for signed and unsigned 32-bit quantities. */
-typedef uint32_t Elf32_Word;
-typedef int32_t Elf32_Sword;
-typedef uint32_t Elf64_Word;
-typedef int32_t Elf64_Sword;
-
-/* Types for signed and unsigned 64-bit quantities. */
-typedef uint64_t Elf32_Xword;
-typedef int64_t Elf32_Sxword;
-typedef uint64_t Elf64_Xword;
-typedef int64_t Elf64_Sxword;
-
-/* Type of addresses. */
-typedef uint32_t Elf32_Addr;
-typedef uint64_t Elf64_Addr;
-
-/* Type of file offsets. */
-typedef uint32_t Elf32_Off;
-typedef uint64_t Elf64_Off;
-
-/* Type for section indices, which are 16-bit quantities. */
-typedef uint16_t Elf32_Section;
-typedef uint16_t Elf64_Section;
-
-/* Type for version symbol information. */
-typedef Elf32_Half Elf32_Versym;
-typedef Elf64_Half Elf64_Versym;
-
-
-/* The ELF file header. This appears at the start of every ELF file. */
-
-#define EI_NIDENT (16)
-
-typedef struct
-{
- unsigned char e_ident[EI_NIDENT]; /* Magic number and other info */
- Elf32_Half e_type; /* Object file type */
- Elf32_Half e_machine; /* Architecture */
- Elf32_Word e_version; /* Object file version */
- Elf32_Addr e_entry; /* Entry point virtual address */
- Elf32_Off e_phoff; /* Program header table file offset */
- Elf32_Off e_shoff; /* Section header table file offset */
- Elf32_Word e_flags; /* Processor-specific flags */
- Elf32_Half e_ehsize; /* ELF header size in bytes */
- Elf32_Half e_phentsize; /* Program header table entry size */
- Elf32_Half e_phnum; /* Program header table entry count */
- Elf32_Half e_shentsize; /* Section header table entry size */
- Elf32_Half e_shnum; /* Section header table entry count */
- Elf32_Half e_shstrndx; /* Section header string table index */
-} Elf32_Ehdr;
-
-typedef struct
-{
- unsigned char e_ident[EI_NIDENT]; /* Magic number and other info */
- Elf64_Half e_type; /* Object file type */
- Elf64_Half e_machine; /* Architecture */
- Elf64_Word e_version; /* Object file version */
- Elf64_Addr e_entry; /* Entry point virtual address */
- Elf64_Off e_phoff; /* Program header table file offset */
- Elf64_Off e_shoff; /* Section header table file offset */
- Elf64_Word e_flags; /* Processor-specific flags */
- Elf64_Half e_ehsize; /* ELF header size in bytes */
- Elf64_Half e_phentsize; /* Program header table entry size */
- Elf64_Half e_phnum; /* Program header table entry count */
- Elf64_Half e_shentsize; /* Section header table entry size */
- Elf64_Half e_shnum; /* Section header table entry count */
- Elf64_Half e_shstrndx; /* Section header string table index */
-} Elf64_Ehdr;
-
-/* Fields in the e_ident array. The EI_* macros are indices into the
- array. The macros under each EI_* macro are the values the byte
- may have. */
-
-#define EI_MAG0 0 /* File identification byte 0 index */
-#define ELFMAG0 0x7f /* Magic number byte 0 */
-
-#define EI_MAG1 1 /* File identification byte 1 index */
-#define ELFMAG1 'E' /* Magic number byte 1 */
-
-#define EI_MAG2 2 /* File identification byte 2 index */
-#define ELFMAG2 'L' /* Magic number byte 2 */
-
-#define EI_MAG3 3 /* File identification byte 3 index */
-#define ELFMAG3 'F' /* Magic number byte 3 */
-
-/* Conglomeration of the identification bytes, for easy testing as a word. */
-#define ELFMAG "\177ELF"
-#define SELFMAG 4
-
-#define EI_CLASS 4 /* File class byte index */
-#define ELFCLASSNONE 0 /* Invalid class */
-#define ELFCLASS32 1 /* 32-bit objects */
-#define ELFCLASS64 2 /* 64-bit objects */
-#define ELFCLASSNUM 3
-
-#define EI_DATA 5 /* Data encoding byte index */
-#define ELFDATANONE 0 /* Invalid data encoding */
-#define ELFDATA2LSB 1 /* 2's complement, little endian */
-#define ELFDATA2MSB 2 /* 2's complement, big endian */
-#define ELFDATANUM 3
-
-#define EI_VERSION 6 /* File version byte index */
- /* Value must be EV_CURRENT */
-
-#define EI_OSABI 7 /* OS ABI identification */
-#define ELFOSABI_NONE 0 /* UNIX System V ABI */
-#define ELFOSABI_SYSV 0 /* Alias. */
-#define ELFOSABI_HPUX 1 /* HP-UX */
-#define ELFOSABI_NETBSD 2 /* NetBSD. */
-#define ELFOSABI_GNU 3 /* Object uses GNU ELF extensions. */
-#define ELFOSABI_LINUX ELFOSABI_GNU /* Compatibility alias. */
-#define ELFOSABI_SOLARIS 6 /* Sun Solaris. */
-#define ELFOSABI_AIX 7 /* IBM AIX. */
-#define ELFOSABI_IRIX 8 /* SGI Irix. */
-#define ELFOSABI_FREEBSD 9 /* FreeBSD. */
-#define ELFOSABI_TRU64 10 /* Compaq TRU64 UNIX. */
-#define ELFOSABI_MODESTO 11 /* Novell Modesto. */
-#define ELFOSABI_OPENBSD 12 /* OpenBSD. */
-#define ELFOSABI_ARM_AEABI 64 /* ARM EABI */
-#define ELFOSABI_ARM 97 /* ARM */
-#define ELFOSABI_STANDALONE 255 /* Standalone (embedded) application */
-
-#define EI_ABIVERSION 8 /* ABI version */
-
-#define EI_PAD 9 /* Byte index of padding bytes */
-
-/* Legal values for e_type (object file type). */
-
-#define ET_NONE 0 /* No file type */
-#define ET_REL 1 /* Relocatable file */
-#define ET_EXEC 2 /* Executable file */
-#define ET_DYN 3 /* Shared object file */
-#define ET_CORE 4 /* Core file */
-#define ET_NUM 5 /* Number of defined types */
-#define ET_LOOS 0xfe00 /* OS-specific range start */
-#define ET_HIOS 0xfeff /* OS-specific range end */
-#define ET_LOPROC 0xff00 /* Processor-specific range start */
-#define ET_HIPROC 0xffff /* Processor-specific range end */
-
-/* Legal values for e_machine (architecture). */
-
-#define EM_NONE 0 /* No machine */
-#define EM_M32 1 /* AT&T WE 32100 */
-#define EM_SPARC 2 /* SUN SPARC */
-#define EM_386 3 /* Intel 80386 */
-#define EM_68K 4 /* Motorola m68k family */
-#define EM_88K 5 /* Motorola m88k family */
-#define EM_IAMCU 6 /* Intel MCU */
-#define EM_860 7 /* Intel 80860 */
-#define EM_MIPS 8 /* MIPS R3000 big-endian */
-#define EM_S370 9 /* IBM System/370 */
-#define EM_MIPS_RS3_LE 10 /* MIPS R3000 little-endian */
- /* reserved 11-14 */
-#define EM_PARISC 15 /* HPPA */
- /* reserved 16 */
-#define EM_VPP500 17 /* Fujitsu VPP500 */
-#define EM_SPARC32PLUS 18 /* Sun's "v8plus" */
-#define EM_960 19 /* Intel 80960 */
-#define EM_PPC 20 /* PowerPC */
-#define EM_PPC64 21 /* PowerPC 64-bit */
-#define EM_S390 22 /* IBM S390 */
-#define EM_SPU 23 /* IBM SPU/SPC */
- /* reserved 24-35 */
-#define EM_V800 36 /* NEC V800 series */
-#define EM_FR20 37 /* Fujitsu FR20 */
-#define EM_RH32 38 /* TRW RH-32 */
-#define EM_RCE 39 /* Motorola RCE */
-#define EM_ARM 40 /* ARM */
-#define EM_FAKE_ALPHA 41 /* Digital Alpha */
-#define EM_SH 42 /* Hitachi SH */
-#define EM_SPARCV9 43 /* SPARC v9 64-bit */
-#define EM_TRICORE 44 /* Siemens Tricore */
-#define EM_ARC 45 /* Argonaut RISC Core */
-#define EM_H8_300 46 /* Hitachi H8/300 */
-#define EM_H8_300H 47 /* Hitachi H8/300H */
-#define EM_H8S 48 /* Hitachi H8S */
-#define EM_H8_500 49 /* Hitachi H8/500 */
-#define EM_IA_64 50 /* Intel Merced */
-#define EM_MIPS_X 51 /* Stanford MIPS-X */
-#define EM_COLDFIRE 52 /* Motorola Coldfire */
-#define EM_68HC12 53 /* Motorola M68HC12 */
-#define EM_MMA 54 /* Fujitsu MMA Multimedia Accelerator */
-#define EM_PCP 55 /* Siemens PCP */
-#define EM_NCPU 56 /* Sony nCPU embeeded RISC */
-#define EM_NDR1 57 /* Denso NDR1 microprocessor */
-#define EM_STARCORE 58 /* Motorola Start*Core processor */
-#define EM_ME16 59 /* Toyota ME16 processor */
-#define EM_ST100 60 /* STMicroelectronic ST100 processor */
-#define EM_TINYJ 61 /* Advanced Logic Corp. Tinyj emb.fam */
-#define EM_X86_64 62 /* AMD x86-64 architecture */
-#define EM_PDSP 63 /* Sony DSP Processor */
-#define EM_PDP10 64 /* Digital PDP-10 */
-#define EM_PDP11 65 /* Digital PDP-11 */
-#define EM_FX66 66 /* Siemens FX66 microcontroller */
-#define EM_ST9PLUS 67 /* STMicroelectronics ST9+ 8/16 mc */
-#define EM_ST7 68 /* STmicroelectronics ST7 8 bit mc */
-#define EM_68HC16 69 /* Motorola MC68HC16 microcontroller */
-#define EM_68HC11 70 /* Motorola MC68HC11 microcontroller */
-#define EM_68HC08 71 /* Motorola MC68HC08 microcontroller */
-#define EM_68HC05 72 /* Motorola MC68HC05 microcontroller */
-#define EM_SVX 73 /* Silicon Graphics SVx */
-#define EM_ST19 74 /* STMicroelectronics ST19 8 bit mc */
-#define EM_VAX 75 /* Digital VAX */
-#define EM_CRIS 76 /* Axis Communications 32-bit emb.proc */
-#define EM_JAVELIN 77 /* Infineon Technologies 32-bit emb.proc */
-#define EM_FIREPATH 78 /* Element 14 64-bit DSP Processor */
-#define EM_ZSP 79 /* LSI Logic 16-bit DSP Processor */
-#define EM_MMIX 80 /* Donald Knuth's educational 64-bit proc */
-#define EM_HUANY 81 /* Harvard University machine-independent object files */
-#define EM_PRISM 82 /* SiTera Prism */
-#define EM_AVR 83 /* Atmel AVR 8-bit microcontroller */
-#define EM_FR30 84 /* Fujitsu FR30 */
-#define EM_D10V 85 /* Mitsubishi D10V */
-#define EM_D30V 86 /* Mitsubishi D30V */
-#define EM_V850 87 /* NEC v850 */
-#define EM_M32R 88 /* Mitsubishi M32R */
-#define EM_MN10300 89 /* Matsushita MN10300 */
-#define EM_MN10200 90 /* Matsushita MN10200 */
-#define EM_PJ 91 /* picoJava */
-#define EM_OPENRISC 92 /* OpenRISC 32-bit embedded processor */
-#define EM_ARC_COMPACT 93 /* ARC International ARCompact */
-#define EM_XTENSA 94 /* Tensilica Xtensa Architecture */
-#define EM_VIDEOCORE 95 /* Alphamosaic VideoCore */
-#define EM_TMM_GPP 96 /* Thompson Multimedia General Purpose Proc */
-#define EM_NS32K 97 /* National Semi. 32000 */
-#define EM_TPC 98 /* Tenor Network TPC */
-#define EM_SNP1K 99 /* Trebia SNP 1000 */
-#define EM_ST200 100 /* STMicroelectronics ST200 */
-#define EM_IP2K 101 /* Ubicom IP2xxx */
-#define EM_MAX 102 /* MAX processor */
-#define EM_CR 103 /* National Semi. CompactRISC */
-#define EM_F2MC16 104 /* Fujitsu F2MC16 */
-#define EM_MSP430 105 /* Texas Instruments msp430 */
-#define EM_BLACKFIN 106 /* Analog Devices Blackfin DSP */
-#define EM_SE_C33 107 /* Seiko Epson S1C33 family */
-#define EM_SEP 108 /* Sharp embedded microprocessor */
-#define EM_ARCA 109 /* Arca RISC */
-#define EM_UNICORE 110 /* PKU-Unity & MPRC Peking Uni. mc series */
-#define EM_EXCESS 111 /* eXcess configurable cpu */
-#define EM_DXP 112 /* Icera Semi. Deep Execution Processor */
-#define EM_ALTERA_NIOS2 113 /* Altera Nios II */
-#define EM_CRX 114 /* National Semi. CompactRISC CRX */
-#define EM_XGATE 115 /* Motorola XGATE */
-#define EM_C166 116 /* Infineon C16x/XC16x */
-#define EM_M16C 117 /* Renesas M16C */
-#define EM_DSPIC30F 118 /* Microchip Technology dsPIC30F */
-#define EM_CE 119 /* Freescale Communication Engine RISC */
-#define EM_M32C 120 /* Renesas M32C */
- /* reserved 121-130 */
-#define EM_TSK3000 131 /* Altium TSK3000 */
-#define EM_RS08 132 /* Freescale RS08 */
-#define EM_SHARC 133 /* Analog Devices SHARC family */
-#define EM_ECOG2 134 /* Cyan Technology eCOG2 */
-#define EM_SCORE7 135 /* Sunplus S+core7 RISC */
-#define EM_DSP24 136 /* New Japan Radio (NJR) 24-bit DSP */
-#define EM_VIDEOCORE3 137 /* Broadcom VideoCore III */
-#define EM_LATTICEMICO32 138 /* RISC for Lattice FPGA */
-#define EM_SE_C17 139 /* Seiko Epson C17 */
-#define EM_TI_C6000 140 /* Texas Instruments TMS320C6000 DSP */
-#define EM_TI_C2000 141 /* Texas Instruments TMS320C2000 DSP */
-#define EM_TI_C5500 142 /* Texas Instruments TMS320C55x DSP */
-#define EM_TI_ARP32 143 /* Texas Instruments App. Specific RISC */
-#define EM_TI_PRU 144 /* Texas Instruments Prog. Realtime Unit */
- /* reserved 145-159 */
-#define EM_MMDSP_PLUS 160 /* STMicroelectronics 64bit VLIW DSP */
-#define EM_CYPRESS_M8C 161 /* Cypress M8C */
-#define EM_R32C 162 /* Renesas R32C */
-#define EM_TRIMEDIA 163 /* NXP Semi. TriMedia */
-#define EM_QDSP6 164 /* QUALCOMM DSP6 */
-#define EM_8051 165 /* Intel 8051 and variants */
-#define EM_STXP7X 166 /* STMicroelectronics STxP7x */
-#define EM_NDS32 167 /* Andes Tech. compact code emb. RISC */
-#define EM_ECOG1X 168 /* Cyan Technology eCOG1X */
-#define EM_MAXQ30 169 /* Dallas Semi. MAXQ30 mc */
-#define EM_XIMO16 170 /* New Japan Radio (NJR) 16-bit DSP */
-#define EM_MANIK 171 /* M2000 Reconfigurable RISC */
-#define EM_CRAYNV2 172 /* Cray NV2 vector architecture */
-#define EM_RX 173 /* Renesas RX */
-#define EM_METAG 174 /* Imagination Tech. META */
-#define EM_MCST_ELBRUS 175 /* MCST Elbrus */
-#define EM_ECOG16 176 /* Cyan Technology eCOG16 */
-#define EM_CR16 177 /* National Semi. CompactRISC CR16 */
-#define EM_ETPU 178 /* Freescale Extended Time Processing Unit */
-#define EM_SLE9X 179 /* Infineon Tech. SLE9X */
-#define EM_L10M 180 /* Intel L10M */
-#define EM_K10M 181 /* Intel K10M */
- /* reserved 182 */
-#define EM_AARCH64 183 /* ARM AARCH64 */
- /* reserved 184 */
-#define EM_AVR32 185 /* Amtel 32-bit microprocessor */
-#define EM_STM8 186 /* STMicroelectronics STM8 */
-#define EM_TILE64 187 /* Tileta TILE64 */
-#define EM_TILEPRO 188 /* Tilera TILEPro */
-#define EM_MICROBLAZE 189 /* Xilinx MicroBlaze */
-#define EM_CUDA 190 /* NVIDIA CUDA */
-#define EM_TILEGX 191 /* Tilera TILE-Gx */
-#define EM_CLOUDSHIELD 192 /* CloudShield */
-#define EM_COREA_1ST 193 /* KIPO-KAIST Core-A 1st gen. */
-#define EM_COREA_2ND 194 /* KIPO-KAIST Core-A 2nd gen. */
-#define EM_ARC_COMPACT2 195 /* Synopsys ARCompact V2 */
-#define EM_OPEN8 196 /* Open8 RISC */
-#define EM_RL78 197 /* Renesas RL78 */
-#define EM_VIDEOCORE5 198 /* Broadcom VideoCore V */
-#define EM_78KOR 199 /* Renesas 78KOR */
-#define EM_56800EX 200 /* Freescale 56800EX DSC */
-#define EM_BA1 201 /* Beyond BA1 */
-#define EM_BA2 202 /* Beyond BA2 */
-#define EM_XCORE 203 /* XMOS xCORE */
-#define EM_MCHP_PIC 204 /* Microchip 8-bit PIC(r) */
- /* reserved 205-209 */
-#define EM_KM32 210 /* KM211 KM32 */
-#define EM_KMX32 211 /* KM211 KMX32 */
-#define EM_EMX16 212 /* KM211 KMX16 */
-#define EM_EMX8 213 /* KM211 KMX8 */
-#define EM_KVARC 214 /* KM211 KVARC */
-#define EM_CDP 215 /* Paneve CDP */
-#define EM_COGE 216 /* Cognitive Smart Memory Processor */
-#define EM_COOL 217 /* Bluechip CoolEngine */
-#define EM_NORC 218 /* Nanoradio Optimized RISC */
-#define EM_CSR_KALIMBA 219 /* CSR Kalimba */
-#define EM_Z80 220 /* Zilog Z80 */
-#define EM_VISIUM 221 /* Controls and Data Services VISIUMcore */
-#define EM_FT32 222 /* FTDI Chip FT32 */
-#define EM_MOXIE 223 /* Moxie processor */
-#define EM_AMDGPU 224 /* AMD GPU */
- /* reserved 225-242 */
-#define EM_RISCV 243 /* RISC-V */
-
-#define EM_BPF 247 /* Linux BPF -- in-kernel virtual machine */
-
-#define EM_NUM 248
-
-/* Old spellings/synonyms. */
-
-#define EM_ARC_A5 EM_ARC_COMPACT
-
-/* If it is necessary to assign new unofficial EM_* values, please
- pick large random numbers (0x8523, 0xa7f2, etc.) to minimize the
- chances of collision with official or non-GNU unofficial values. */
-
-#define EM_ALPHA 0x9026
-
-/* Legal values for e_version (version). */
-
-#define EV_NONE 0 /* Invalid ELF version */
-#define EV_CURRENT 1 /* Current version */
-#define EV_NUM 2
-
-/* Section header. */
-
-typedef struct
-{
- Elf32_Word sh_name; /* Section name (string tbl index) */
- Elf32_Word sh_type; /* Section type */
- Elf32_Word sh_flags; /* Section flags */
- Elf32_Addr sh_addr; /* Section virtual addr at execution */
- Elf32_Off sh_offset; /* Section file offset */
- Elf32_Word sh_size; /* Section size in bytes */
- Elf32_Word sh_link; /* Link to another section */
- Elf32_Word sh_info; /* Additional section information */
- Elf32_Word sh_addralign; /* Section alignment */
- Elf32_Word sh_entsize; /* Entry size if section holds table */
-} Elf32_Shdr;
-
-typedef struct
-{
- Elf64_Word sh_name; /* Section name (string tbl index) */
- Elf64_Word sh_type; /* Section type */
- Elf64_Xword sh_flags; /* Section flags */
- Elf64_Addr sh_addr; /* Section virtual addr at execution */
- Elf64_Off sh_offset; /* Section file offset */
- Elf64_Xword sh_size; /* Section size in bytes */
- Elf64_Word sh_link; /* Link to another section */
- Elf64_Word sh_info; /* Additional section information */
- Elf64_Xword sh_addralign; /* Section alignment */
- Elf64_Xword sh_entsize; /* Entry size if section holds table */
-} Elf64_Shdr;
-
-/* Special section indices. */
-
-#define SHN_UNDEF 0 /* Undefined section */
-#define SHN_LORESERVE 0xff00 /* Start of reserved indices */
-#define SHN_LOPROC 0xff00 /* Start of processor-specific */
-#define SHN_BEFORE 0xff00 /* Order section before all others
- (Solaris). */
-#define SHN_AFTER 0xff01 /* Order section after all others
- (Solaris). */
-#define SHN_HIPROC 0xff1f /* End of processor-specific */
-#define SHN_LOOS 0xff20 /* Start of OS-specific */
-#define SHN_HIOS 0xff3f /* End of OS-specific */
-#define SHN_ABS 0xfff1 /* Associated symbol is absolute */
-#define SHN_COMMON 0xfff2 /* Associated symbol is common */
-#define SHN_XINDEX 0xffff /* Index is in extra table. */
-#define SHN_HIRESERVE 0xffff /* End of reserved indices */
-
-/* Legal values for sh_type (section type). */
-
-#define SHT_NULL 0 /* Section header table entry unused */
-#define SHT_PROGBITS 1 /* Program data */
-#define SHT_SYMTAB 2 /* Symbol table */
-#define SHT_STRTAB 3 /* String table */
-#define SHT_RELA 4 /* Relocation entries with addends */
-#define SHT_HASH 5 /* Symbol hash table */
-#define SHT_DYNAMIC 6 /* Dynamic linking information */
-#define SHT_NOTE 7 /* Notes */
-#define SHT_NOBITS 8 /* Program space with no data (bss) */
-#define SHT_REL 9 /* Relocation entries, no addends */
-#define SHT_SHLIB 10 /* Reserved */
-#define SHT_DYNSYM 11 /* Dynamic linker symbol table */
-#define SHT_INIT_ARRAY 14 /* Array of constructors */
-#define SHT_FINI_ARRAY 15 /* Array of destructors */
-#define SHT_PREINIT_ARRAY 16 /* Array of pre-constructors */
-#define SHT_GROUP 17 /* Section group */
-#define SHT_SYMTAB_SHNDX 18 /* Extended section indeces */
-#define SHT_NUM 19 /* Number of defined types. */
-#define SHT_LOOS 0x60000000 /* Start OS-specific. */
-#define SHT_GNU_ATTRIBUTES 0x6ffffff5 /* Object attributes. */
-#define SHT_GNU_HASH 0x6ffffff6 /* GNU-style hash table. */
-#define SHT_GNU_LIBLIST 0x6ffffff7 /* Prelink library list */
-#define SHT_CHECKSUM 0x6ffffff8 /* Checksum for DSO content. */
-#define SHT_LOSUNW 0x6ffffffa /* Sun-specific low bound. */
-#define SHT_SUNW_move 0x6ffffffa
-#define SHT_SUNW_COMDAT 0x6ffffffb
-#define SHT_SUNW_syminfo 0x6ffffffc
-#define SHT_GNU_verdef 0x6ffffffd /* Version definition section. */
-#define SHT_GNU_verneed 0x6ffffffe /* Version needs section. */
-#define SHT_GNU_versym 0x6fffffff /* Version symbol table. */
-#define SHT_HISUNW 0x6fffffff /* Sun-specific high bound. */
-#define SHT_HIOS 0x6fffffff /* End OS-specific type */
-#define SHT_LOPROC 0x70000000 /* Start of processor-specific */
-#define SHT_HIPROC 0x7fffffff /* End of processor-specific */
-#define SHT_LOUSER 0x80000000 /* Start of application-specific */
-#define SHT_HIUSER 0x8fffffff /* End of application-specific */
-
-/* Legal values for sh_flags (section flags). */
-
-#define SHF_WRITE (1 << 0) /* Writable */
-#define SHF_ALLOC (1 << 1) /* Occupies memory during execution */
-#define SHF_EXECINSTR (1 << 2) /* Executable */
-#define SHF_MERGE (1 << 4) /* Might be merged */
-#define SHF_STRINGS (1 << 5) /* Contains nul-terminated strings */
-#define SHF_INFO_LINK (1 << 6) /* `sh_info' contains SHT index */
-#define SHF_LINK_ORDER (1 << 7) /* Preserve order after combining */
-#define SHF_OS_NONCONFORMING (1 << 8) /* Non-standard OS specific handling
- required */
-#define SHF_GROUP (1 << 9) /* Section is member of a group. */
-#define SHF_TLS (1 << 10) /* Section hold thread-local data. */
-#define SHF_COMPRESSED (1 << 11) /* Section with compressed data. */
-#define SHF_MASKOS 0x0ff00000 /* OS-specific. */
-#define SHF_MASKPROC 0xf0000000 /* Processor-specific */
-#define SHF_ORDERED (1 << 30) /* Special ordering requirement
- (Solaris). */
-#define SHF_EXCLUDE (1U << 31) /* Section is excluded unless
- referenced or allocated (Solaris).*/
-
-/* Section compression header. Used when SHF_COMPRESSED is set. */
-
-typedef struct
-{
- Elf32_Word ch_type; /* Compression format. */
- Elf32_Word ch_size; /* Uncompressed data size. */
- Elf32_Word ch_addralign; /* Uncompressed data alignment. */
-} Elf32_Chdr;
-
-typedef struct
-{
- Elf64_Word ch_type; /* Compression format. */
- Elf64_Word ch_reserved;
- Elf64_Xword ch_size; /* Uncompressed data size. */
- Elf64_Xword ch_addralign; /* Uncompressed data alignment. */
-} Elf64_Chdr;
-
-/* Legal values for ch_type (compression algorithm). */
-#define ELFCOMPRESS_ZLIB 1 /* ZLIB/DEFLATE algorithm. */
-#define ELFCOMPRESS_LOOS 0x60000000 /* Start of OS-specific. */
-#define ELFCOMPRESS_HIOS 0x6fffffff /* End of OS-specific. */
-#define ELFCOMPRESS_LOPROC 0x70000000 /* Start of processor-specific. */
-#define ELFCOMPRESS_HIPROC 0x7fffffff /* End of processor-specific. */
-
-/* Section group handling. */
-#define GRP_COMDAT 0x1 /* Mark group as COMDAT. */
-
-/* Symbol table entry. */
-
-typedef struct
-{
- Elf32_Word st_name; /* Symbol name (string tbl index) */
- Elf32_Addr st_value; /* Symbol value */
- Elf32_Word st_size; /* Symbol size */
- unsigned char st_info; /* Symbol type and binding */
- unsigned char st_other; /* Symbol visibility */
- Elf32_Section st_shndx; /* Section index */
-} Elf32_Sym;
-
-typedef struct
-{
- Elf64_Word st_name; /* Symbol name (string tbl index) */
- unsigned char st_info; /* Symbol type and binding */
- unsigned char st_other; /* Symbol visibility */
- Elf64_Section st_shndx; /* Section index */
- Elf64_Addr st_value; /* Symbol value */
- Elf64_Xword st_size; /* Symbol size */
-} Elf64_Sym;
-
-/* The syminfo section if available contains additional information about
- every dynamic symbol. */
-
-typedef struct
-{
- Elf32_Half si_boundto; /* Direct bindings, symbol bound to */
- Elf32_Half si_flags; /* Per symbol flags */
-} Elf32_Syminfo;
-
-typedef struct
-{
- Elf64_Half si_boundto; /* Direct bindings, symbol bound to */
- Elf64_Half si_flags; /* Per symbol flags */
-} Elf64_Syminfo;
-
-/* Possible values for si_boundto. */
-#define SYMINFO_BT_SELF 0xffff /* Symbol bound to self */
-#define SYMINFO_BT_PARENT 0xfffe /* Symbol bound to parent */
-#define SYMINFO_BT_LOWRESERVE 0xff00 /* Beginning of reserved entries */
-
-/* Possible bitmasks for si_flags. */
-#define SYMINFO_FLG_DIRECT 0x0001 /* Direct bound symbol */
-#define SYMINFO_FLG_PASSTHRU 0x0002 /* Pass-thru symbol for translator */
-#define SYMINFO_FLG_COPY 0x0004 /* Symbol is a copy-reloc */
-#define SYMINFO_FLG_LAZYLOAD 0x0008 /* Symbol bound to object to be lazy
- loaded */
-/* Syminfo version values. */
-#define SYMINFO_NONE 0
-#define SYMINFO_CURRENT 1
-#define SYMINFO_NUM 2
-
-
-/* How to extract and insert information held in the st_info field. */
-
-#define ELF32_ST_BIND(val) (((unsigned char) (val)) >> 4)
-#define ELF32_ST_TYPE(val) ((val) & 0xf)
-#define ELF32_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf))
-
-/* Both Elf32_Sym and Elf64_Sym use the same one-byte st_info field. */
-#define ELF64_ST_BIND(val) ELF32_ST_BIND (val)
-#define ELF64_ST_TYPE(val) ELF32_ST_TYPE (val)
-#define ELF64_ST_INFO(bind, type) ELF32_ST_INFO ((bind), (type))
-
-/* Legal values for ST_BIND subfield of st_info (symbol binding). */
-
-#define STB_LOCAL 0 /* Local symbol */
-#define STB_GLOBAL 1 /* Global symbol */
-#define STB_WEAK 2 /* Weak symbol */
-#define STB_NUM 3 /* Number of defined types. */
-#define STB_LOOS 10 /* Start of OS-specific */
-#define STB_GNU_UNIQUE 10 /* Unique symbol. */
-#define STB_HIOS 12 /* End of OS-specific */
-#define STB_LOPROC 13 /* Start of processor-specific */
-#define STB_HIPROC 15 /* End of processor-specific */
-
-/* Legal values for ST_TYPE subfield of st_info (symbol type). */
-
-#define STT_NOTYPE 0 /* Symbol type is unspecified */
-#define STT_OBJECT 1 /* Symbol is a data object */
-#define STT_FUNC 2 /* Symbol is a code object */
-#define STT_SECTION 3 /* Symbol associated with a section */
-#define STT_FILE 4 /* Symbol's name is file name */
-#define STT_COMMON 5 /* Symbol is a common data object */
-#define STT_TLS 6 /* Symbol is thread-local data object*/
-#define STT_NUM 7 /* Number of defined types. */
-#define STT_LOOS 10 /* Start of OS-specific */
-#define STT_GNU_IFUNC 10 /* Symbol is indirect code object */
-#define STT_HIOS 12 /* End of OS-specific */
-#define STT_LOPROC 13 /* Start of processor-specific */
-#define STT_HIPROC 15 /* End of processor-specific */
-
-
-/* Symbol table indices are found in the hash buckets and chain table
- of a symbol hash table section. This special index value indicates
- the end of a chain, meaning no further symbols are found in that bucket. */
-
-#define STN_UNDEF 0 /* End of a chain. */
-
-
-/* How to extract and insert information held in the st_other field. */
-
-#define ELF32_ST_VISIBILITY(o) ((o) & 0x03)
-
-/* For ELF64 the definitions are the same. */
-#define ELF64_ST_VISIBILITY(o) ELF32_ST_VISIBILITY (o)
-
-/* Symbol visibility specification encoded in the st_other field. */
-#define STV_DEFAULT 0 /* Default symbol visibility rules */
-#define STV_INTERNAL 1 /* Processor specific hidden class */
-#define STV_HIDDEN 2 /* Sym unavailable in other modules */
-#define STV_PROTECTED 3 /* Not preemptible, not exported */
-
-
-/* Relocation table entry without addend (in section of type SHT_REL). */
-
-typedef struct
-{
- Elf32_Addr r_offset; /* Address */
- Elf32_Word r_info; /* Relocation type and symbol index */
-} Elf32_Rel;
-
-/* I have seen two different definitions of the Elf64_Rel and
- Elf64_Rela structures, so we'll leave them out until Novell (or
- whoever) gets their act together. */
-/* The following, at least, is used on Sparc v9, MIPS, and Alpha. */
-
-typedef struct
-{
- Elf64_Addr r_offset; /* Address */
- Elf64_Xword r_info; /* Relocation type and symbol index */
-} Elf64_Rel;
-
-/* Relocation table entry with addend (in section of type SHT_RELA). */
-
-typedef struct
-{
- Elf32_Addr r_offset; /* Address */
- Elf32_Word r_info; /* Relocation type and symbol index */
- Elf32_Sword r_addend; /* Addend */
-} Elf32_Rela;
-
-typedef struct
-{
- Elf64_Addr r_offset; /* Address */
- Elf64_Xword r_info; /* Relocation type and symbol index */
- Elf64_Sxword r_addend; /* Addend */
-} Elf64_Rela;
-
-/* How to extract and insert information held in the r_info field. */
-
-#define ELF32_R_SYM(val) ((val) >> 8)
-#define ELF32_R_TYPE(val) ((val) & 0xff)
-#define ELF32_R_INFO(sym, type) (((sym) << 8) + ((type) & 0xff))
-
-#define ELF64_R_SYM(i) ((i) >> 32)
-#define ELF64_R_TYPE(i) ((i) & 0xffffffff)
-#define ELF64_R_INFO(sym,type) ((((Elf64_Xword) (sym)) << 32) + (type))
-
-/* Program segment header. */
-
-typedef struct
-{
- Elf32_Word p_type; /* Segment type */
- Elf32_Off p_offset; /* Segment file offset */
- Elf32_Addr p_vaddr; /* Segment virtual address */
- Elf32_Addr p_paddr; /* Segment physical address */
- Elf32_Word p_filesz; /* Segment size in file */
- Elf32_Word p_memsz; /* Segment size in memory */
- Elf32_Word p_flags; /* Segment flags */
- Elf32_Word p_align; /* Segment alignment */
-} Elf32_Phdr;
-
-typedef struct
-{
- Elf64_Word p_type; /* Segment type */
- Elf64_Word p_flags; /* Segment flags */
- Elf64_Off p_offset; /* Segment file offset */
- Elf64_Addr p_vaddr; /* Segment virtual address */
- Elf64_Addr p_paddr; /* Segment physical address */
- Elf64_Xword p_filesz; /* Segment size in file */
- Elf64_Xword p_memsz; /* Segment size in memory */
- Elf64_Xword p_align; /* Segment alignment */
-} Elf64_Phdr;
-
-/* Special value for e_phnum. This indicates that the real number of
- program headers is too large to fit into e_phnum. Instead the real
- value is in the field sh_info of section 0. */
-
-#define PN_XNUM 0xffff
-
-/* Legal values for p_type (segment type). */
-
-#define PT_NULL 0 /* Program header table entry unused */
-#define PT_LOAD 1 /* Loadable program segment */
-#define PT_DYNAMIC 2 /* Dynamic linking information */
-#define PT_INTERP 3 /* Program interpreter */
-#define PT_NOTE 4 /* Auxiliary information */
-#define PT_SHLIB 5 /* Reserved */
-#define PT_PHDR 6 /* Entry for header table itself */
-#define PT_TLS 7 /* Thread-local storage segment */
-#define PT_NUM 8 /* Number of defined types */
-#define PT_LOOS 0x60000000 /* Start of OS-specific */
-#define PT_GNU_EH_FRAME 0x6474e550 /* GCC .eh_frame_hdr segment */
-#define PT_GNU_STACK 0x6474e551 /* Indicates stack executability */
-#define PT_GNU_RELRO 0x6474e552 /* Read-only after relocation */
-#define PT_LOSUNW 0x6ffffffa
-#define PT_SUNWBSS 0x6ffffffa /* Sun Specific segment */
-#define PT_SUNWSTACK 0x6ffffffb /* Stack segment */
-#define PT_HISUNW 0x6fffffff
-#define PT_HIOS 0x6fffffff /* End of OS-specific */
-#define PT_LOPROC 0x70000000 /* Start of processor-specific */
-#define PT_HIPROC 0x7fffffff /* End of processor-specific */
-
-/* Legal values for p_flags (segment flags). */
-
-#define PF_X (1 << 0) /* Segment is executable */
-#define PF_W (1 << 1) /* Segment is writable */
-#define PF_R (1 << 2) /* Segment is readable */
-#define PF_MASKOS 0x0ff00000 /* OS-specific */
-#define PF_MASKPROC 0xf0000000 /* Processor-specific */
-
-/* Legal values for note segment descriptor types for core files. */
-
-#define NT_PRSTATUS 1 /* Contains copy of prstatus struct */
-#define NT_FPREGSET 2 /* Contains copy of fpregset struct */
-#define NT_PRPSINFO 3 /* Contains copy of prpsinfo struct */
-#define NT_PRXREG 4 /* Contains copy of prxregset struct */
-#define NT_TASKSTRUCT 4 /* Contains copy of task structure */
-#define NT_PLATFORM 5 /* String from sysinfo(SI_PLATFORM) */
-#define NT_AUXV 6 /* Contains copy of auxv array */
-#define NT_GWINDOWS 7 /* Contains copy of gwindows struct */
-#define NT_ASRS 8 /* Contains copy of asrset struct */
-#define NT_PSTATUS 10 /* Contains copy of pstatus struct */
-#define NT_PSINFO 13 /* Contains copy of psinfo struct */
-#define NT_PRCRED 14 /* Contains copy of prcred struct */
-#define NT_UTSNAME 15 /* Contains copy of utsname struct */
-#define NT_LWPSTATUS 16 /* Contains copy of lwpstatus struct */
-#define NT_LWPSINFO 17 /* Contains copy of lwpinfo struct */
-#define NT_PRFPXREG 20 /* Contains copy of fprxregset struct */
-#define NT_SIGINFO 0x53494749 /* Contains copy of siginfo_t,
- size might increase */
-#define NT_FILE 0x46494c45 /* Contains information about mapped
- files */
-#define NT_PRXFPREG 0x46e62b7f /* Contains copy of user_fxsr_struct */
-#define NT_PPC_VMX 0x100 /* PowerPC Altivec/VMX registers */
-#define NT_PPC_SPE 0x101 /* PowerPC SPE/EVR registers */
-#define NT_PPC_VSX 0x102 /* PowerPC VSX registers */
-#define NT_386_TLS 0x200 /* i386 TLS slots (struct user_desc) */
-#define NT_386_IOPERM 0x201 /* x86 io permission bitmap (1=deny) */
-#define NT_X86_XSTATE 0x202 /* x86 extended state using xsave */
-#define NT_S390_HIGH_GPRS 0x300 /* s390 upper register halves */
-#define NT_S390_TIMER 0x301 /* s390 timer register */
-#define NT_S390_TODCMP 0x302 /* s390 TOD clock comparator register */
-#define NT_S390_TODPREG 0x303 /* s390 TOD programmable register */
-#define NT_S390_CTRS 0x304 /* s390 control registers */
-#define NT_S390_PREFIX 0x305 /* s390 prefix register */
-#define NT_S390_LAST_BREAK 0x306 /* s390 breaking event address */
-#define NT_S390_SYSTEM_CALL 0x307 /* s390 system call restart data */
-#define NT_S390_TDB 0x308 /* s390 transaction diagnostic block */
-#define NT_ARM_VFP 0x400 /* ARM VFP/NEON registers */
-#define NT_ARM_TLS 0x401 /* ARM TLS register */
-#define NT_ARM_HW_BREAK 0x402 /* ARM hardware breakpoint registers */
-#define NT_ARM_HW_WATCH 0x403 /* ARM hardware watchpoint registers */
-#define NT_ARM_SYSTEM_CALL 0x404 /* ARM system call number */
-
-/* Legal values for the note segment descriptor types for object files. */
-
-#define NT_VERSION 1 /* Contains a version string. */
-
-
-/* Dynamic section entry. */
-
-typedef struct
-{
- Elf32_Sword d_tag; /* Dynamic entry type */
- union
- {
- Elf32_Word d_val; /* Integer value */
- Elf32_Addr d_ptr; /* Address value */
- } d_un;
-} Elf32_Dyn;
-
-typedef struct
-{
- Elf64_Sxword d_tag; /* Dynamic entry type */
- union
- {
- Elf64_Xword d_val; /* Integer value */
- Elf64_Addr d_ptr; /* Address value */
- } d_un;
-} Elf64_Dyn;
-
-/* Legal values for d_tag (dynamic entry type). */
-
-#define DT_NULL 0 /* Marks end of dynamic section */
-#define DT_NEEDED 1 /* Name of needed library */
-#define DT_PLTRELSZ 2 /* Size in bytes of PLT relocs */
-#define DT_PLTGOT 3 /* Processor defined value */
-#define DT_HASH 4 /* Address of symbol hash table */
-#define DT_STRTAB 5 /* Address of string table */
-#define DT_SYMTAB 6 /* Address of symbol table */
-#define DT_RELA 7 /* Address of Rela relocs */
-#define DT_RELASZ 8 /* Total size of Rela relocs */
-#define DT_RELAENT 9 /* Size of one Rela reloc */
-#define DT_STRSZ 10 /* Size of string table */
-#define DT_SYMENT 11 /* Size of one symbol table entry */
-#define DT_INIT 12 /* Address of init function */
-#define DT_FINI 13 /* Address of termination function */
-#define DT_SONAME 14 /* Name of shared object */
-#define DT_RPATH 15 /* Library search path (deprecated) */
-#define DT_SYMBOLIC 16 /* Start symbol search here */
-#define DT_REL 17 /* Address of Rel relocs */
-#define DT_RELSZ 18 /* Total size of Rel relocs */
-#define DT_RELENT 19 /* Size of one Rel reloc */
-#define DT_PLTREL 20 /* Type of reloc in PLT */
-#define DT_DEBUG 21 /* For debugging; unspecified */
-#define DT_TEXTREL 22 /* Reloc might modify .text */
-#define DT_JMPREL 23 /* Address of PLT relocs */
-#define DT_BIND_NOW 24 /* Process relocations of object */
-#define DT_INIT_ARRAY 25 /* Array with addresses of init fct */
-#define DT_FINI_ARRAY 26 /* Array with addresses of fini fct */
-#define DT_INIT_ARRAYSZ 27 /* Size in bytes of DT_INIT_ARRAY */
-#define DT_FINI_ARRAYSZ 28 /* Size in bytes of DT_FINI_ARRAY */
-#define DT_RUNPATH 29 /* Library search path */
-#define DT_FLAGS 30 /* Flags for the object being loaded */
-#define DT_ENCODING 32 /* Start of encoded range */
-#define DT_PREINIT_ARRAY 32 /* Array with addresses of preinit fct*/
-#define DT_PREINIT_ARRAYSZ 33 /* size in bytes of DT_PREINIT_ARRAY */
-#define DT_NUM 34 /* Number used */
-#define DT_LOOS 0x6000000d /* Start of OS-specific */
-#define DT_HIOS 0x6ffff000 /* End of OS-specific */
-#define DT_LOPROC 0x70000000 /* Start of processor-specific */
-#define DT_HIPROC 0x7fffffff /* End of processor-specific */
-#define DT_PROCNUM DT_MIPS_NUM /* Most used by any processor */
-
-/* DT_* entries which fall between DT_VALRNGHI & DT_VALRNGLO use the
- Dyn.d_un.d_val field of the Elf*_Dyn structure. This follows Sun's
- approach. */
-#define DT_VALRNGLO 0x6ffffd00
-#define DT_GNU_PRELINKED 0x6ffffdf5 /* Prelinking timestamp */
-#define DT_GNU_CONFLICTSZ 0x6ffffdf6 /* Size of conflict section */
-#define DT_GNU_LIBLISTSZ 0x6ffffdf7 /* Size of library list */
-#define DT_CHECKSUM 0x6ffffdf8
-#define DT_PLTPADSZ 0x6ffffdf9
-#define DT_MOVEENT 0x6ffffdfa
-#define DT_MOVESZ 0x6ffffdfb
-#define DT_FEATURE_1 0x6ffffdfc /* Feature selection (DTF_*). */
-#define DT_POSFLAG_1 0x6ffffdfd /* Flags for DT_* entries, effecting
- the following DT_* entry. */
-#define DT_SYMINSZ 0x6ffffdfe /* Size of syminfo table (in bytes) */
-#define DT_SYMINENT 0x6ffffdff /* Entry size of syminfo */
-#define DT_VALRNGHI 0x6ffffdff
-#define DT_VALTAGIDX(tag) (DT_VALRNGHI - (tag)) /* Reverse order! */
-#define DT_VALNUM 12
-
-/* DT_* entries which fall between DT_ADDRRNGHI & DT_ADDRRNGLO use the
- Dyn.d_un.d_ptr field of the Elf*_Dyn structure.
-
- If any adjustment is made to the ELF object after it has been
- built these entries will need to be adjusted. */
-#define DT_ADDRRNGLO 0x6ffffe00
-#define DT_GNU_HASH 0x6ffffef5 /* GNU-style hash table. */
-#define DT_TLSDESC_PLT 0x6ffffef6
-#define DT_TLSDESC_GOT 0x6ffffef7
-#define DT_GNU_CONFLICT 0x6ffffef8 /* Start of conflict section */
-#define DT_GNU_LIBLIST 0x6ffffef9 /* Library list */
-#define DT_CONFIG 0x6ffffefa /* Configuration information. */
-#define DT_DEPAUDIT 0x6ffffefb /* Dependency auditing. */
-#define DT_AUDIT 0x6ffffefc /* Object auditing. */
-#define DT_PLTPAD 0x6ffffefd /* PLT padding. */
-#define DT_MOVETAB 0x6ffffefe /* Move table. */
-#define DT_SYMINFO 0x6ffffeff /* Syminfo table. */
-#define DT_ADDRRNGHI 0x6ffffeff
-#define DT_ADDRTAGIDX(tag) (DT_ADDRRNGHI - (tag)) /* Reverse order! */
-#define DT_ADDRNUM 11
-
-/* The versioning entry types. The next are defined as part of the
- GNU extension. */
-#define DT_VERSYM 0x6ffffff0
-
-#define DT_RELACOUNT 0x6ffffff9
-#define DT_RELCOUNT 0x6ffffffa
-
-/* These were chosen by Sun. */
-#define DT_FLAGS_1 0x6ffffffb /* State flags, see DF_1_* below. */
-#define DT_VERDEF 0x6ffffffc /* Address of version definition
- table */
-#define DT_VERDEFNUM 0x6ffffffd /* Number of version definitions */
-#define DT_VERNEED 0x6ffffffe /* Address of table with needed
- versions */
-#define DT_VERNEEDNUM 0x6fffffff /* Number of needed versions */
-#define DT_VERSIONTAGIDX(tag) (DT_VERNEEDNUM - (tag)) /* Reverse order! */
-#define DT_VERSIONTAGNUM 16
-
-/* Sun added these machine-independent extensions in the "processor-specific"
- range. Be compatible. */
-#define DT_AUXILIARY 0x7ffffffd /* Shared object to load before self */
-#define DT_FILTER 0x7fffffff /* Shared object to get values from */
-#define DT_EXTRATAGIDX(tag) ((Elf32_Word)-((Elf32_Sword) (tag) <<1>>1)-1)
-#define DT_EXTRANUM 3
-
-/* Values of `d_un.d_val' in the DT_FLAGS entry. */
-#define DF_ORIGIN 0x00000001 /* Object may use DF_ORIGIN */
-#define DF_SYMBOLIC 0x00000002 /* Symbol resolutions starts here */
-#define DF_TEXTREL 0x00000004 /* Object contains text relocations */
-#define DF_BIND_NOW 0x00000008 /* No lazy binding for this object */
-#define DF_STATIC_TLS 0x00000010 /* Module uses the static TLS model */
-
-/* State flags selectable in the `d_un.d_val' element of the DT_FLAGS_1
- entry in the dynamic section. */
-#define DF_1_NOW 0x00000001 /* Set RTLD_NOW for this object. */
-#define DF_1_GLOBAL 0x00000002 /* Set RTLD_GLOBAL for this object. */
-#define DF_1_GROUP 0x00000004 /* Set RTLD_GROUP for this object. */
-#define DF_1_NODELETE 0x00000008 /* Set RTLD_NODELETE for this object.*/
-#define DF_1_LOADFLTR 0x00000010 /* Trigger filtee loading at runtime.*/
-#define DF_1_INITFIRST 0x00000020 /* Set RTLD_INITFIRST for this object*/
-#define DF_1_NOOPEN 0x00000040 /* Set RTLD_NOOPEN for this object. */
-#define DF_1_ORIGIN 0x00000080 /* $ORIGIN must be handled. */
-#define DF_1_DIRECT 0x00000100 /* Direct binding enabled. */
-#define DF_1_TRANS 0x00000200
-#define DF_1_INTERPOSE 0x00000400 /* Object is used to interpose. */
-#define DF_1_NODEFLIB 0x00000800 /* Ignore default lib search path. */
-#define DF_1_NODUMP 0x00001000 /* Object can't be dldump'ed. */
-#define DF_1_CONFALT 0x00002000 /* Configuration alternative created.*/
-#define DF_1_ENDFILTEE 0x00004000 /* Filtee terminates filters search. */
-#define DF_1_DISPRELDNE 0x00008000 /* Disp reloc applied at build time. */
-#define DF_1_DISPRELPND 0x00010000 /* Disp reloc applied at run-time. */
-#define DF_1_NODIRECT 0x00020000 /* Object has no-direct binding. */
-#define DF_1_IGNMULDEF 0x00040000
-#define DF_1_NOKSYMS 0x00080000
-#define DF_1_NOHDR 0x00100000
-#define DF_1_EDITED 0x00200000 /* Object is modified after built. */
-#define DF_1_NORELOC 0x00400000
-#define DF_1_SYMINTPOSE 0x00800000 /* Object has individual interposers. */
-#define DF_1_GLOBAUDIT 0x01000000 /* Global auditing required. */
-#define DF_1_SINGLETON 0x02000000 /* Singleton symbols are used. */
-
-/* Flags for the feature selection in DT_FEATURE_1. */
-#define DTF_1_PARINIT 0x00000001
-#define DTF_1_CONFEXP 0x00000002
-
-/* Flags in the DT_POSFLAG_1 entry effecting only the next DT_* entry. */
-#define DF_P1_LAZYLOAD 0x00000001 /* Lazyload following object. */
-#define DF_P1_GROUPPERM 0x00000002 /* Symbols from next object are not
- generally available. */
-
-/* Version definition sections. */
-
-typedef struct
-{
- Elf32_Half vd_version; /* Version revision */
- Elf32_Half vd_flags; /* Version information */
- Elf32_Half vd_ndx; /* Version Index */
- Elf32_Half vd_cnt; /* Number of associated aux entries */
- Elf32_Word vd_hash; /* Version name hash value */
- Elf32_Word vd_aux; /* Offset in bytes to verdaux array */
- Elf32_Word vd_next; /* Offset in bytes to next verdef
- entry */
-} Elf32_Verdef;
-
-typedef struct
-{
- Elf64_Half vd_version; /* Version revision */
- Elf64_Half vd_flags; /* Version information */
- Elf64_Half vd_ndx; /* Version Index */
- Elf64_Half vd_cnt; /* Number of associated aux entries */
- Elf64_Word vd_hash; /* Version name hash value */
- Elf64_Word vd_aux; /* Offset in bytes to verdaux array */
- Elf64_Word vd_next; /* Offset in bytes to next verdef
- entry */
-} Elf64_Verdef;
-
-
-/* Legal values for vd_version (version revision). */
-#define VER_DEF_NONE 0 /* No version */
-#define VER_DEF_CURRENT 1 /* Current version */
-#define VER_DEF_NUM 2 /* Given version number */
-
-/* Legal values for vd_flags (version information flags). */
-#define VER_FLG_BASE 0x1 /* Version definition of file itself */
-#define VER_FLG_WEAK 0x2 /* Weak version identifier */
-
-/* Versym symbol index values. */
-#define VER_NDX_LOCAL 0 /* Symbol is local. */
-#define VER_NDX_GLOBAL 1 /* Symbol is global. */
-#define VER_NDX_LORESERVE 0xff00 /* Beginning of reserved entries. */
-#define VER_NDX_ELIMINATE 0xff01 /* Symbol is to be eliminated. */
-
-/* Auxialiary version information. */
-
-typedef struct
-{
- Elf32_Word vda_name; /* Version or dependency names */
- Elf32_Word vda_next; /* Offset in bytes to next verdaux
- entry */
-} Elf32_Verdaux;
-
-typedef struct
-{
- Elf64_Word vda_name; /* Version or dependency names */
- Elf64_Word vda_next; /* Offset in bytes to next verdaux
- entry */
-} Elf64_Verdaux;
-
-
-/* Version dependency section. */
-
-typedef struct
-{
- Elf32_Half vn_version; /* Version of structure */
- Elf32_Half vn_cnt; /* Number of associated aux entries */
- Elf32_Word vn_file; /* Offset of filename for this
- dependency */
- Elf32_Word vn_aux; /* Offset in bytes to vernaux array */
- Elf32_Word vn_next; /* Offset in bytes to next verneed
- entry */
-} Elf32_Verneed;
-
-typedef struct
-{
- Elf64_Half vn_version; /* Version of structure */
- Elf64_Half vn_cnt; /* Number of associated aux entries */
- Elf64_Word vn_file; /* Offset of filename for this
- dependency */
- Elf64_Word vn_aux; /* Offset in bytes to vernaux array */
- Elf64_Word vn_next; /* Offset in bytes to next verneed
- entry */
-} Elf64_Verneed;
-
-
-/* Legal values for vn_version (version revision). */
-#define VER_NEED_NONE 0 /* No version */
-#define VER_NEED_CURRENT 1 /* Current version */
-#define VER_NEED_NUM 2 /* Given version number */
-
-/* Auxiliary needed version information. */
-
-typedef struct
-{
- Elf32_Word vna_hash; /* Hash value of dependency name */
- Elf32_Half vna_flags; /* Dependency specific information */
- Elf32_Half vna_other; /* Unused */
- Elf32_Word vna_name; /* Dependency name string offset */
- Elf32_Word vna_next; /* Offset in bytes to next vernaux
- entry */
-} Elf32_Vernaux;
-
-typedef struct
-{
- Elf64_Word vna_hash; /* Hash value of dependency name */
- Elf64_Half vna_flags; /* Dependency specific information */
- Elf64_Half vna_other; /* Unused */
- Elf64_Word vna_name; /* Dependency name string offset */
- Elf64_Word vna_next; /* Offset in bytes to next vernaux
- entry */
-} Elf64_Vernaux;
-
-
-/* Legal values for vna_flags. */
-#define VER_FLG_WEAK 0x2 /* Weak version identifier */
-
-
-/* Auxiliary vector. */
-
-/* This vector is normally only used by the program interpreter. The
- usual definition in an ABI supplement uses the name auxv_t. The
- vector is not usually defined in a standard <elf.h> file, but it
- can't hurt. We rename it to avoid conflicts. The sizes of these
- types are an arrangement between the exec server and the program
- interpreter, so we don't fully specify them here. */
-
-typedef struct
-{
- uint32_t a_type; /* Entry type */
- union
- {
- uint32_t a_val; /* Integer value */
- /* We use to have pointer elements added here. We cannot do that,
- though, since it does not work when using 32-bit definitions
- on 64-bit platforms and vice versa. */
- } a_un;
-} Elf32_auxv_t;
-
-typedef struct
-{
- uint64_t a_type; /* Entry type */
- union
- {
- uint64_t a_val; /* Integer value */
- /* We use to have pointer elements added here. We cannot do that,
- though, since it does not work when using 32-bit definitions
- on 64-bit platforms and vice versa. */
- } a_un;
-} Elf64_auxv_t;
-
-/* Legal values for a_type (entry type). */
-
-#define AT_NULL 0 /* End of vector */
-#define AT_IGNORE 1 /* Entry should be ignored */
-#define AT_EXECFD 2 /* File descriptor of program */
-#define AT_PHDR 3 /* Program headers for program */
-#define AT_PHENT 4 /* Size of program header entry */
-#define AT_PHNUM 5 /* Number of program headers */
-#define AT_PAGESZ 6 /* System page size */
-#define AT_BASE 7 /* Base address of interpreter */
-#define AT_FLAGS 8 /* Flags */
-#define AT_ENTRY 9 /* Entry point of program */
-#define AT_NOTELF 10 /* Program is not ELF */
-#define AT_UID 11 /* Real uid */
-#define AT_EUID 12 /* Effective uid */
-#define AT_GID 13 /* Real gid */
-#define AT_EGID 14 /* Effective gid */
-#define AT_CLKTCK 17 /* Frequency of times() */
-
-/* Some more special a_type values describing the hardware. */
-#define AT_PLATFORM 15 /* String identifying platform. */
-#define AT_HWCAP 16 /* Machine-dependent hints about
- processor capabilities. */
-
-/* This entry gives some information about the FPU initialization
- performed by the kernel. */
-#define AT_FPUCW 18 /* Used FPU control word. */
-
-/* Cache block sizes. */
-#define AT_DCACHEBSIZE 19 /* Data cache block size. */
-#define AT_ICACHEBSIZE 20 /* Instruction cache block size. */
-#define AT_UCACHEBSIZE 21 /* Unified cache block size. */
-
-/* A special ignored value for PPC, used by the kernel to control the
- interpretation of the AUXV. Must be > 16. */
-#define AT_IGNOREPPC 22 /* Entry should be ignored. */
-
-#define AT_SECURE 23 /* Boolean, was exec setuid-like? */
-
-#define AT_BASE_PLATFORM 24 /* String identifying real platforms.*/
-
-#define AT_RANDOM 25 /* Address of 16 random bytes. */
-
-#define AT_HWCAP2 26 /* More machine-dependent hints about
- processor capabilities. */
-
-#define AT_EXECFN 31 /* Filename of executable. */
-
-/* Pointer to the global system page used for system calls and other
- nice things. */
-#define AT_SYSINFO 32
-#define AT_SYSINFO_EHDR 33
-
-/* Shapes of the caches. Bits 0-3 contains associativity; bits 4-7 contains
- log2 of line size; mask those to get cache size. */
-#define AT_L1I_CACHESHAPE 34
-#define AT_L1D_CACHESHAPE 35
-#define AT_L2_CACHESHAPE 36
-#define AT_L3_CACHESHAPE 37
-
-/* Shapes of the caches, with more room to describe them.
- *GEOMETRY are comprised of cache line size in bytes in the bottom 16 bits
- and the cache associativity in the next 16 bits. */
-#define AT_L1I_CACHESIZE 40
-#define AT_L1I_CACHEGEOMETRY 41
-#define AT_L1D_CACHESIZE 42
-#define AT_L1D_CACHEGEOMETRY 43
-#define AT_L2_CACHESIZE 44
-#define AT_L2_CACHEGEOMETRY 45
-#define AT_L3_CACHESIZE 46
-#define AT_L3_CACHEGEOMETRY 47
-
-/* Note section contents. Each entry in the note section begins with
- a header of a fixed form. */
-
-typedef struct
-{
- Elf32_Word n_namesz; /* Length of the note's name. */
- Elf32_Word n_descsz; /* Length of the note's descriptor. */
- Elf32_Word n_type; /* Type of the note. */
-} Elf32_Nhdr;
-
-typedef struct
-{
- Elf64_Word n_namesz; /* Length of the note's name. */
- Elf64_Word n_descsz; /* Length of the note's descriptor. */
- Elf64_Word n_type; /* Type of the note. */
-} Elf64_Nhdr;
-
-/* Known names of notes. */
-
-/* Solaris entries in the note section have this name. */
-#define ELF_NOTE_SOLARIS "SUNW Solaris"
-
-/* Note entries for GNU systems have this name. */
-#define ELF_NOTE_GNU "GNU"
-
-
-/* Defined types of notes for Solaris. */
-
-/* Value of descriptor (one word) is desired pagesize for the binary. */
-#define ELF_NOTE_PAGESIZE_HINT 1
-
-
-/* Defined note types for GNU systems. */
-
-/* ABI information. The descriptor consists of words:
- word 0: OS descriptor
- word 1: major version of the ABI
- word 2: minor version of the ABI
- word 3: subminor version of the ABI
-*/
-#define NT_GNU_ABI_TAG 1
-#define ELF_NOTE_ABI NT_GNU_ABI_TAG /* Old name. */
-
-/* Known OSes. These values can appear in word 0 of an
- NT_GNU_ABI_TAG note section entry. */
-#define ELF_NOTE_OS_LINUX 0
-#define ELF_NOTE_OS_GNU 1
-#define ELF_NOTE_OS_SOLARIS2 2
-#define ELF_NOTE_OS_FREEBSD 3
-
-/* Synthetic hwcap information. The descriptor begins with two words:
- word 0: number of entries
- word 1: bitmask of enabled entries
- Then follow variable-length entries, one byte followed by a
- '\0'-terminated hwcap name string. The byte gives the bit
- number to test if enabled, (1U << bit) & bitmask. */
-#define NT_GNU_HWCAP 2
-
-/* Build ID bits as generated by ld --build-id.
- The descriptor consists of any nonzero number of bytes. */
-#define NT_GNU_BUILD_ID 3
-
-/* Version note generated by GNU gold containing a version string. */
-#define NT_GNU_GOLD_VERSION 4
-
-
-/* Move records. */
-typedef struct
-{
- Elf32_Xword m_value; /* Symbol value. */
- Elf32_Word m_info; /* Size and index. */
- Elf32_Word m_poffset; /* Symbol offset. */
- Elf32_Half m_repeat; /* Repeat count. */
- Elf32_Half m_stride; /* Stride info. */
-} Elf32_Move;
-
-typedef struct
-{
- Elf64_Xword m_value; /* Symbol value. */
- Elf64_Xword m_info; /* Size and index. */
- Elf64_Xword m_poffset; /* Symbol offset. */
- Elf64_Half m_repeat; /* Repeat count. */
- Elf64_Half m_stride; /* Stride info. */
-} Elf64_Move;
-
-/* Macro to construct move records. */
-#define ELF32_M_SYM(info) ((info) >> 8)
-#define ELF32_M_SIZE(info) ((unsigned char) (info))
-#define ELF32_M_INFO(sym, size) (((sym) << 8) + (unsigned char) (size))
-
-#define ELF64_M_SYM(info) ELF32_M_SYM (info)
-#define ELF64_M_SIZE(info) ELF32_M_SIZE (info)
-#define ELF64_M_INFO(sym, size) ELF32_M_INFO (sym, size)
-
-
-/* Motorola 68k specific definitions. */
-
-/* Values for Elf32_Ehdr.e_flags. */
-#define EF_CPU32 0x00810000
-
-/* m68k relocs. */
-
-#define R_68K_NONE 0 /* No reloc */
-#define R_68K_32 1 /* Direct 32 bit */
-#define R_68K_16 2 /* Direct 16 bit */
-#define R_68K_8 3 /* Direct 8 bit */
-#define R_68K_PC32 4 /* PC relative 32 bit */
-#define R_68K_PC16 5 /* PC relative 16 bit */
-#define R_68K_PC8 6 /* PC relative 8 bit */
-#define R_68K_GOT32 7 /* 32 bit PC relative GOT entry */
-#define R_68K_GOT16 8 /* 16 bit PC relative GOT entry */
-#define R_68K_GOT8 9 /* 8 bit PC relative GOT entry */
-#define R_68K_GOT32O 10 /* 32 bit GOT offset */
-#define R_68K_GOT16O 11 /* 16 bit GOT offset */
-#define R_68K_GOT8O 12 /* 8 bit GOT offset */
-#define R_68K_PLT32 13 /* 32 bit PC relative PLT address */
-#define R_68K_PLT16 14 /* 16 bit PC relative PLT address */
-#define R_68K_PLT8 15 /* 8 bit PC relative PLT address */
-#define R_68K_PLT32O 16 /* 32 bit PLT offset */
-#define R_68K_PLT16O 17 /* 16 bit PLT offset */
-#define R_68K_PLT8O 18 /* 8 bit PLT offset */
-#define R_68K_COPY 19 /* Copy symbol at runtime */
-#define R_68K_GLOB_DAT 20 /* Create GOT entry */
-#define R_68K_JMP_SLOT 21 /* Create PLT entry */
-#define R_68K_RELATIVE 22 /* Adjust by program base */
-#define R_68K_TLS_GD32 25 /* 32 bit GOT offset for GD */
-#define R_68K_TLS_GD16 26 /* 16 bit GOT offset for GD */
-#define R_68K_TLS_GD8 27 /* 8 bit GOT offset for GD */
-#define R_68K_TLS_LDM32 28 /* 32 bit GOT offset for LDM */
-#define R_68K_TLS_LDM16 29 /* 16 bit GOT offset for LDM */
-#define R_68K_TLS_LDM8 30 /* 8 bit GOT offset for LDM */
-#define R_68K_TLS_LDO32 31 /* 32 bit module-relative offset */
-#define R_68K_TLS_LDO16 32 /* 16 bit module-relative offset */
-#define R_68K_TLS_LDO8 33 /* 8 bit module-relative offset */
-#define R_68K_TLS_IE32 34 /* 32 bit GOT offset for IE */
-#define R_68K_TLS_IE16 35 /* 16 bit GOT offset for IE */
-#define R_68K_TLS_IE8 36 /* 8 bit GOT offset for IE */
-#define R_68K_TLS_LE32 37 /* 32 bit offset relative to
- static TLS block */
-#define R_68K_TLS_LE16 38 /* 16 bit offset relative to
- static TLS block */
-#define R_68K_TLS_LE8 39 /* 8 bit offset relative to
- static TLS block */
-#define R_68K_TLS_DTPMOD32 40 /* 32 bit module number */
-#define R_68K_TLS_DTPREL32 41 /* 32 bit module-relative offset */
-#define R_68K_TLS_TPREL32 42 /* 32 bit TP-relative offset */
-/* Keep this the last entry. */
-#define R_68K_NUM 43
-
-/* Intel 80386 specific definitions. */
-
-/* i386 relocs. */
-
-#define R_386_NONE 0 /* No reloc */
-#define R_386_32 1 /* Direct 32 bit */
-#define R_386_PC32 2 /* PC relative 32 bit */
-#define R_386_GOT32 3 /* 32 bit GOT entry */
-#define R_386_PLT32 4 /* 32 bit PLT address */
-#define R_386_COPY 5 /* Copy symbol at runtime */
-#define R_386_GLOB_DAT 6 /* Create GOT entry */
-#define R_386_JMP_SLOT 7 /* Create PLT entry */
-#define R_386_RELATIVE 8 /* Adjust by program base */
-#define R_386_GOTOFF 9 /* 32 bit offset to GOT */
-#define R_386_GOTPC 10 /* 32 bit PC relative offset to GOT */
-#define R_386_32PLT 11
-#define R_386_TLS_TPOFF 14 /* Offset in static TLS block */
-#define R_386_TLS_IE 15 /* Address of GOT entry for static TLS
- block offset */
-#define R_386_TLS_GOTIE 16 /* GOT entry for static TLS block
- offset */
-#define R_386_TLS_LE 17 /* Offset relative to static TLS
- block */
-#define R_386_TLS_GD 18 /* Direct 32 bit for GNU version of
- general dynamic thread local data */
-#define R_386_TLS_LDM 19 /* Direct 32 bit for GNU version of
- local dynamic thread local data
- in LE code */
-#define R_386_16 20
-#define R_386_PC16 21
-#define R_386_8 22
-#define R_386_PC8 23
-#define R_386_TLS_GD_32 24 /* Direct 32 bit for general dynamic
- thread local data */
-#define R_386_TLS_GD_PUSH 25 /* Tag for pushl in GD TLS code */
-#define R_386_TLS_GD_CALL 26 /* Relocation for call to
- __tls_get_addr() */
-#define R_386_TLS_GD_POP 27 /* Tag for popl in GD TLS code */
-#define R_386_TLS_LDM_32 28 /* Direct 32 bit for local dynamic
- thread local data in LE code */
-#define R_386_TLS_LDM_PUSH 29 /* Tag for pushl in LDM TLS code */
-#define R_386_TLS_LDM_CALL 30 /* Relocation for call to
- __tls_get_addr() in LDM code */
-#define R_386_TLS_LDM_POP 31 /* Tag for popl in LDM TLS code */
-#define R_386_TLS_LDO_32 32 /* Offset relative to TLS block */
-#define R_386_TLS_IE_32 33 /* GOT entry for negated static TLS
- block offset */
-#define R_386_TLS_LE_32 34 /* Negated offset relative to static
- TLS block */
-#define R_386_TLS_DTPMOD32 35 /* ID of module containing symbol */
-#define R_386_TLS_DTPOFF32 36 /* Offset in TLS block */
-#define R_386_TLS_TPOFF32 37 /* Negated offset in static TLS block */
-#define R_386_SIZE32 38 /* 32-bit symbol size */
-#define R_386_TLS_GOTDESC 39 /* GOT offset for TLS descriptor. */
-#define R_386_TLS_DESC_CALL 40 /* Marker of call through TLS
- descriptor for
- relaxation. */
-#define R_386_TLS_DESC 41 /* TLS descriptor containing
- pointer to code and to
- argument, returning the TLS
- offset for the symbol. */
-#define R_386_IRELATIVE 42 /* Adjust indirectly by program base */
-#define R_386_GOT32X 43 /* Load from 32 bit GOT entry,
- relaxable. */
-/* Keep this the last entry. */
-#define R_386_NUM 44
-
-/* SUN SPARC specific definitions. */
-
-/* Legal values for ST_TYPE subfield of st_info (symbol type). */
-
-#define STT_SPARC_REGISTER 13 /* Global register reserved to app. */
-
-/* Values for Elf64_Ehdr.e_flags. */
-
-#define EF_SPARCV9_MM 3
-#define EF_SPARCV9_TSO 0
-#define EF_SPARCV9_PSO 1
-#define EF_SPARCV9_RMO 2
-#define EF_SPARC_LEDATA 0x800000 /* little endian data */
-#define EF_SPARC_EXT_MASK 0xFFFF00
-#define EF_SPARC_32PLUS 0x000100 /* generic V8+ features */
-#define EF_SPARC_SUN_US1 0x000200 /* Sun UltraSPARC1 extensions */
-#define EF_SPARC_HAL_R1 0x000400 /* HAL R1 extensions */
-#define EF_SPARC_SUN_US3 0x000800 /* Sun UltraSPARCIII extensions */
-
-/* SPARC relocs. */
-
-#define R_SPARC_NONE 0 /* No reloc */
-#define R_SPARC_8 1 /* Direct 8 bit */
-#define R_SPARC_16 2 /* Direct 16 bit */
-#define R_SPARC_32 3 /* Direct 32 bit */
-#define R_SPARC_DISP8 4 /* PC relative 8 bit */
-#define R_SPARC_DISP16 5 /* PC relative 16 bit */
-#define R_SPARC_DISP32 6 /* PC relative 32 bit */
-#define R_SPARC_WDISP30 7 /* PC relative 30 bit shifted */
-#define R_SPARC_WDISP22 8 /* PC relative 22 bit shifted */
-#define R_SPARC_HI22 9 /* High 22 bit */
-#define R_SPARC_22 10 /* Direct 22 bit */
-#define R_SPARC_13 11 /* Direct 13 bit */
-#define R_SPARC_LO10 12 /* Truncated 10 bit */
-#define R_SPARC_GOT10 13 /* Truncated 10 bit GOT entry */
-#define R_SPARC_GOT13 14 /* 13 bit GOT entry */
-#define R_SPARC_GOT22 15 /* 22 bit GOT entry shifted */
-#define R_SPARC_PC10 16 /* PC relative 10 bit truncated */
-#define R_SPARC_PC22 17 /* PC relative 22 bit shifted */
-#define R_SPARC_WPLT30 18 /* 30 bit PC relative PLT address */
-#define R_SPARC_COPY 19 /* Copy symbol at runtime */
-#define R_SPARC_GLOB_DAT 20 /* Create GOT entry */
-#define R_SPARC_JMP_SLOT 21 /* Create PLT entry */
-#define R_SPARC_RELATIVE 22 /* Adjust by program base */
-#define R_SPARC_UA32 23 /* Direct 32 bit unaligned */
-
-/* Additional Sparc64 relocs. */
-
-#define R_SPARC_PLT32 24 /* Direct 32 bit ref to PLT entry */
-#define R_SPARC_HIPLT22 25 /* High 22 bit PLT entry */
-#define R_SPARC_LOPLT10 26 /* Truncated 10 bit PLT entry */
-#define R_SPARC_PCPLT32 27 /* PC rel 32 bit ref to PLT entry */
-#define R_SPARC_PCPLT22 28 /* PC rel high 22 bit PLT entry */
-#define R_SPARC_PCPLT10 29 /* PC rel trunc 10 bit PLT entry */
-#define R_SPARC_10 30 /* Direct 10 bit */
-#define R_SPARC_11 31 /* Direct 11 bit */
-#define R_SPARC_64 32 /* Direct 64 bit */
-#define R_SPARC_OLO10 33 /* 10bit with secondary 13bit addend */
-#define R_SPARC_HH22 34 /* Top 22 bits of direct 64 bit */
-#define R_SPARC_HM10 35 /* High middle 10 bits of ... */
-#define R_SPARC_LM22 36 /* Low middle 22 bits of ... */
-#define R_SPARC_PC_HH22 37 /* Top 22 bits of pc rel 64 bit */
-#define R_SPARC_PC_HM10 38 /* High middle 10 bit of ... */
-#define R_SPARC_PC_LM22 39 /* Low miggle 22 bits of ... */
-#define R_SPARC_WDISP16 40 /* PC relative 16 bit shifted */
-#define R_SPARC_WDISP19 41 /* PC relative 19 bit shifted */
-#define R_SPARC_GLOB_JMP 42 /* was part of v9 ABI but was removed */
-#define R_SPARC_7 43 /* Direct 7 bit */
-#define R_SPARC_5 44 /* Direct 5 bit */
-#define R_SPARC_6 45 /* Direct 6 bit */
-#define R_SPARC_DISP64 46 /* PC relative 64 bit */
-#define R_SPARC_PLT64 47 /* Direct 64 bit ref to PLT entry */
-#define R_SPARC_HIX22 48 /* High 22 bit complemented */
-#define R_SPARC_LOX10 49 /* Truncated 11 bit complemented */
-#define R_SPARC_H44 50 /* Direct high 12 of 44 bit */
-#define R_SPARC_M44 51 /* Direct mid 22 of 44 bit */
-#define R_SPARC_L44 52 /* Direct low 10 of 44 bit */
-#define R_SPARC_REGISTER 53 /* Global register usage */
-#define R_SPARC_UA64 54 /* Direct 64 bit unaligned */
-#define R_SPARC_UA16 55 /* Direct 16 bit unaligned */
-#define R_SPARC_TLS_GD_HI22 56
-#define R_SPARC_TLS_GD_LO10 57
-#define R_SPARC_TLS_GD_ADD 58
-#define R_SPARC_TLS_GD_CALL 59
-#define R_SPARC_TLS_LDM_HI22 60
-#define R_SPARC_TLS_LDM_LO10 61
-#define R_SPARC_TLS_LDM_ADD 62
-#define R_SPARC_TLS_LDM_CALL 63
-#define R_SPARC_TLS_LDO_HIX22 64
-#define R_SPARC_TLS_LDO_LOX10 65
-#define R_SPARC_TLS_LDO_ADD 66
-#define R_SPARC_TLS_IE_HI22 67
-#define R_SPARC_TLS_IE_LO10 68
-#define R_SPARC_TLS_IE_LD 69
-#define R_SPARC_TLS_IE_LDX 70
-#define R_SPARC_TLS_IE_ADD 71
-#define R_SPARC_TLS_LE_HIX22 72
-#define R_SPARC_TLS_LE_LOX10 73
-#define R_SPARC_TLS_DTPMOD32 74
-#define R_SPARC_TLS_DTPMOD64 75
-#define R_SPARC_TLS_DTPOFF32 76
-#define R_SPARC_TLS_DTPOFF64 77
-#define R_SPARC_TLS_TPOFF32 78
-#define R_SPARC_TLS_TPOFF64 79
-#define R_SPARC_GOTDATA_HIX22 80
-#define R_SPARC_GOTDATA_LOX10 81
-#define R_SPARC_GOTDATA_OP_HIX22 82
-#define R_SPARC_GOTDATA_OP_LOX10 83
-#define R_SPARC_GOTDATA_OP 84
-#define R_SPARC_H34 85
-#define R_SPARC_SIZE32 86
-#define R_SPARC_SIZE64 87
-#define R_SPARC_WDISP10 88
-#define R_SPARC_JMP_IREL 248
-#define R_SPARC_IRELATIVE 249
-#define R_SPARC_GNU_VTINHERIT 250
-#define R_SPARC_GNU_VTENTRY 251
-#define R_SPARC_REV32 252
-/* Keep this the last entry. */
-#define R_SPARC_NUM 253
-
-/* For Sparc64, legal values for d_tag of Elf64_Dyn. */
-
-#define DT_SPARC_REGISTER 0x70000001
-#define DT_SPARC_NUM 2
-
-/* MIPS R3000 specific definitions. */
-
-/* Legal values for e_flags field of Elf32_Ehdr. */
-
-#define EF_MIPS_NOREORDER 1 /* A .noreorder directive was used. */
-#define EF_MIPS_PIC 2 /* Contains PIC code. */
-#define EF_MIPS_CPIC 4 /* Uses PIC calling sequence. */
-#define EF_MIPS_XGOT 8
-#define EF_MIPS_64BIT_WHIRL 16
-#define EF_MIPS_ABI2 32
-#define EF_MIPS_ABI_ON32 64
-#define EF_MIPS_FP64 512 /* Uses FP64 (12 callee-saved). */
-#define EF_MIPS_NAN2008 1024 /* Uses IEEE 754-2008 NaN encoding. */
-#define EF_MIPS_ARCH 0xf0000000 /* MIPS architecture level. */
-
-/* Legal values for MIPS architecture level. */
-
-#define EF_MIPS_ARCH_1 0x00000000 /* -mips1 code. */
-#define EF_MIPS_ARCH_2 0x10000000 /* -mips2 code. */
-#define EF_MIPS_ARCH_3 0x20000000 /* -mips3 code. */
-#define EF_MIPS_ARCH_4 0x30000000 /* -mips4 code. */
-#define EF_MIPS_ARCH_5 0x40000000 /* -mips5 code. */
-#define EF_MIPS_ARCH_32 0x50000000 /* MIPS32 code. */
-#define EF_MIPS_ARCH_64 0x60000000 /* MIPS64 code. */
-#define EF_MIPS_ARCH_32R2 0x70000000 /* MIPS32r2 code. */
-#define EF_MIPS_ARCH_64R2 0x80000000 /* MIPS64r2 code. */
-
-/* The following are unofficial names and should not be used. */
-
-#define E_MIPS_ARCH_1 EF_MIPS_ARCH_1
-#define E_MIPS_ARCH_2 EF_MIPS_ARCH_2
-#define E_MIPS_ARCH_3 EF_MIPS_ARCH_3
-#define E_MIPS_ARCH_4 EF_MIPS_ARCH_4
-#define E_MIPS_ARCH_5 EF_MIPS_ARCH_5
-#define E_MIPS_ARCH_32 EF_MIPS_ARCH_32
-#define E_MIPS_ARCH_64 EF_MIPS_ARCH_64
-
-/* Special section indices. */
-
-#define SHN_MIPS_ACOMMON 0xff00 /* Allocated common symbols. */
-#define SHN_MIPS_TEXT 0xff01 /* Allocated test symbols. */
-#define SHN_MIPS_DATA 0xff02 /* Allocated data symbols. */
-#define SHN_MIPS_SCOMMON 0xff03 /* Small common symbols. */
-#define SHN_MIPS_SUNDEFINED 0xff04 /* Small undefined symbols. */
-
-/* Legal values for sh_type field of Elf32_Shdr. */
-
-#define SHT_MIPS_LIBLIST 0x70000000 /* Shared objects used in link. */
-#define SHT_MIPS_MSYM 0x70000001
-#define SHT_MIPS_CONFLICT 0x70000002 /* Conflicting symbols. */
-#define SHT_MIPS_GPTAB 0x70000003 /* Global data area sizes. */
-#define SHT_MIPS_UCODE 0x70000004 /* Reserved for SGI/MIPS compilers */
-#define SHT_MIPS_DEBUG 0x70000005 /* MIPS ECOFF debugging info. */
-#define SHT_MIPS_REGINFO 0x70000006 /* Register usage information. */
-#define SHT_MIPS_PACKAGE 0x70000007
-#define SHT_MIPS_PACKSYM 0x70000008
-#define SHT_MIPS_RELD 0x70000009
-#define SHT_MIPS_IFACE 0x7000000b
-#define SHT_MIPS_CONTENT 0x7000000c
-#define SHT_MIPS_OPTIONS 0x7000000d /* Miscellaneous options. */
-#define SHT_MIPS_SHDR 0x70000010
-#define SHT_MIPS_FDESC 0x70000011
-#define SHT_MIPS_EXTSYM 0x70000012
-#define SHT_MIPS_DENSE 0x70000013
-#define SHT_MIPS_PDESC 0x70000014
-#define SHT_MIPS_LOCSYM 0x70000015
-#define SHT_MIPS_AUXSYM 0x70000016
-#define SHT_MIPS_OPTSYM 0x70000017
-#define SHT_MIPS_LOCSTR 0x70000018
-#define SHT_MIPS_LINE 0x70000019
-#define SHT_MIPS_RFDESC 0x7000001a
-#define SHT_MIPS_DELTASYM 0x7000001b
-#define SHT_MIPS_DELTAINST 0x7000001c
-#define SHT_MIPS_DELTACLASS 0x7000001d
-#define SHT_MIPS_DWARF 0x7000001e /* DWARF debugging information. */
-#define SHT_MIPS_DELTADECL 0x7000001f
-#define SHT_MIPS_SYMBOL_LIB 0x70000020
-#define SHT_MIPS_EVENTS 0x70000021 /* Event section. */
-#define SHT_MIPS_TRANSLATE 0x70000022
-#define SHT_MIPS_PIXIE 0x70000023
-#define SHT_MIPS_XLATE 0x70000024
-#define SHT_MIPS_XLATE_DEBUG 0x70000025
-#define SHT_MIPS_WHIRL 0x70000026
-#define SHT_MIPS_EH_REGION 0x70000027
-#define SHT_MIPS_XLATE_OLD 0x70000028
-#define SHT_MIPS_PDR_EXCEPTION 0x70000029
-
-/* Legal values for sh_flags field of Elf32_Shdr. */
-
-#define SHF_MIPS_GPREL 0x10000000 /* Must be in global data area. */
-#define SHF_MIPS_MERGE 0x20000000
-#define SHF_MIPS_ADDR 0x40000000
-#define SHF_MIPS_STRINGS 0x80000000
-#define SHF_MIPS_NOSTRIP 0x08000000
-#define SHF_MIPS_LOCAL 0x04000000
-#define SHF_MIPS_NAMES 0x02000000
-#define SHF_MIPS_NODUPE 0x01000000
-
-
-/* Symbol tables. */
-
-/* MIPS specific values for `st_other'. */
-#define STO_MIPS_DEFAULT 0x0
-#define STO_MIPS_INTERNAL 0x1
-#define STO_MIPS_HIDDEN 0x2
-#define STO_MIPS_PROTECTED 0x3
-#define STO_MIPS_PLT 0x8
-#define STO_MIPS_SC_ALIGN_UNUSED 0xff
-
-/* MIPS specific values for `st_info'. */
-#define STB_MIPS_SPLIT_COMMON 13
-
-/* Entries found in sections of type SHT_MIPS_GPTAB. */
-
-typedef union
-{
- struct
- {
- Elf32_Word gt_current_g_value; /* -G value used for compilation. */
- Elf32_Word gt_unused; /* Not used. */
- } gt_header; /* First entry in section. */
- struct
- {
- Elf32_Word gt_g_value; /* If this value were used for -G. */
- Elf32_Word gt_bytes; /* This many bytes would be used. */
- } gt_entry; /* Subsequent entries in section. */
-} Elf32_gptab;
-
-/* Entry found in sections of type SHT_MIPS_REGINFO. */
-
-typedef struct
-{
- Elf32_Word ri_gprmask; /* General registers used. */
- Elf32_Word ri_cprmask[4]; /* Coprocessor registers used. */
- Elf32_Sword ri_gp_value; /* $gp register value. */
-} Elf32_RegInfo;
-
-/* Entries found in sections of type SHT_MIPS_OPTIONS. */
-
-typedef struct
-{
- unsigned char kind; /* Determines interpretation of the
- variable part of descriptor. */
- unsigned char size; /* Size of descriptor, including header. */
- Elf32_Section section; /* Section header index of section affected,
- 0 for global options. */
- Elf32_Word info; /* Kind-specific information. */
-} Elf_Options;
-
-/* Values for `kind' field in Elf_Options. */
-
-#define ODK_NULL 0 /* Undefined. */
-#define ODK_REGINFO 1 /* Register usage information. */
-#define ODK_EXCEPTIONS 2 /* Exception processing options. */
-#define ODK_PAD 3 /* Section padding options. */
-#define ODK_HWPATCH 4 /* Hardware workarounds performed */
-#define ODK_FILL 5 /* record the fill value used by the linker. */
-#define ODK_TAGS 6 /* reserve space for desktop tools to write. */
-#define ODK_HWAND 7 /* HW workarounds. 'AND' bits when merging. */
-#define ODK_HWOR 8 /* HW workarounds. 'OR' bits when merging. */
-
-/* Values for `info' in Elf_Options for ODK_EXCEPTIONS entries. */
-
-#define OEX_FPU_MIN 0x1f /* FPE's which MUST be enabled. */
-#define OEX_FPU_MAX 0x1f00 /* FPE's which MAY be enabled. */
-#define OEX_PAGE0 0x10000 /* page zero must be mapped. */
-#define OEX_SMM 0x20000 /* Force sequential memory mode? */
-#define OEX_FPDBUG 0x40000 /* Force floating point debug mode? */
-#define OEX_PRECISEFP OEX_FPDBUG
-#define OEX_DISMISS 0x80000 /* Dismiss invalid address faults? */
-
-#define OEX_FPU_INVAL 0x10
-#define OEX_FPU_DIV0 0x08
-#define OEX_FPU_OFLO 0x04
-#define OEX_FPU_UFLO 0x02
-#define OEX_FPU_INEX 0x01
-
-/* Masks for `info' in Elf_Options for an ODK_HWPATCH entry. */
-
-#define OHW_R4KEOP 0x1 /* R4000 end-of-page patch. */
-#define OHW_R8KPFETCH 0x2 /* may need R8000 prefetch patch. */
-#define OHW_R5KEOP 0x4 /* R5000 end-of-page patch. */
-#define OHW_R5KCVTL 0x8 /* R5000 cvt.[ds].l bug. clean=1. */
-
-#define OPAD_PREFIX 0x1
-#define OPAD_POSTFIX 0x2
-#define OPAD_SYMBOL 0x4
-
-/* Entry found in `.options' section. */
-
-typedef struct
-{
- Elf32_Word hwp_flags1; /* Extra flags. */
- Elf32_Word hwp_flags2; /* Extra flags. */
-} Elf_Options_Hw;
-
-/* Masks for `info' in ElfOptions for ODK_HWAND and ODK_HWOR entries. */
-
-#define OHWA0_R4KEOP_CHECKED 0x00000001
-#define OHWA1_R4KEOP_CLEAN 0x00000002
-
-/* MIPS relocs. */
-
-#define R_MIPS_NONE 0 /* No reloc */
-#define R_MIPS_16 1 /* Direct 16 bit */
-#define R_MIPS_32 2 /* Direct 32 bit */
-#define R_MIPS_REL32 3 /* PC relative 32 bit */
-#define R_MIPS_26 4 /* Direct 26 bit shifted */
-#define R_MIPS_HI16 5 /* High 16 bit */
-#define R_MIPS_LO16 6 /* Low 16 bit */
-#define R_MIPS_GPREL16 7 /* GP relative 16 bit */
-#define R_MIPS_LITERAL 8 /* 16 bit literal entry */
-#define R_MIPS_GOT16 9 /* 16 bit GOT entry */
-#define R_MIPS_PC16 10 /* PC relative 16 bit */
-#define R_MIPS_CALL16 11 /* 16 bit GOT entry for function */
-#define R_MIPS_GPREL32 12 /* GP relative 32 bit */
-
-#define R_MIPS_SHIFT5 16
-#define R_MIPS_SHIFT6 17
-#define R_MIPS_64 18
-#define R_MIPS_GOT_DISP 19
-#define R_MIPS_GOT_PAGE 20
-#define R_MIPS_GOT_OFST 21
-#define R_MIPS_GOT_HI16 22
-#define R_MIPS_GOT_LO16 23
-#define R_MIPS_SUB 24
-#define R_MIPS_INSERT_A 25
-#define R_MIPS_INSERT_B 26
-#define R_MIPS_DELETE 27
-#define R_MIPS_HIGHER 28
-#define R_MIPS_HIGHEST 29
-#define R_MIPS_CALL_HI16 30
-#define R_MIPS_CALL_LO16 31
-#define R_MIPS_SCN_DISP 32
-#define R_MIPS_REL16 33
-#define R_MIPS_ADD_IMMEDIATE 34
-#define R_MIPS_PJUMP 35
-#define R_MIPS_RELGOT 36
-#define R_MIPS_JALR 37
-#define R_MIPS_TLS_DTPMOD32 38 /* Module number 32 bit */
-#define R_MIPS_TLS_DTPREL32 39 /* Module-relative offset 32 bit */
-#define R_MIPS_TLS_DTPMOD64 40 /* Module number 64 bit */
-#define R_MIPS_TLS_DTPREL64 41 /* Module-relative offset 64 bit */
-#define R_MIPS_TLS_GD 42 /* 16 bit GOT offset for GD */
-#define R_MIPS_TLS_LDM 43 /* 16 bit GOT offset for LDM */
-#define R_MIPS_TLS_DTPREL_HI16 44 /* Module-relative offset, high 16 bits */
-#define R_MIPS_TLS_DTPREL_LO16 45 /* Module-relative offset, low 16 bits */
-#define R_MIPS_TLS_GOTTPREL 46 /* 16 bit GOT offset for IE */
-#define R_MIPS_TLS_TPREL32 47 /* TP-relative offset, 32 bit */
-#define R_MIPS_TLS_TPREL64 48 /* TP-relative offset, 64 bit */
-#define R_MIPS_TLS_TPREL_HI16 49 /* TP-relative offset, high 16 bits */
-#define R_MIPS_TLS_TPREL_LO16 50 /* TP-relative offset, low 16 bits */
-#define R_MIPS_GLOB_DAT 51
-#define R_MIPS_COPY 126
-#define R_MIPS_JUMP_SLOT 127
-/* Keep this the last entry. */
-#define R_MIPS_NUM 128
-
-/* Legal values for p_type field of Elf32_Phdr. */
-
-#define PT_MIPS_REGINFO 0x70000000 /* Register usage information. */
-#define PT_MIPS_RTPROC 0x70000001 /* Runtime procedure table. */
-#define PT_MIPS_OPTIONS 0x70000002
-#define PT_MIPS_ABIFLAGS 0x70000003 /* FP mode requirement. */
-
-/* Special program header types. */
-
-#define PF_MIPS_LOCAL 0x10000000
-
-/* Legal values for d_tag field of Elf32_Dyn. */
-
-#define DT_MIPS_RLD_VERSION 0x70000001 /* Runtime linker interface version */
-#define DT_MIPS_TIME_STAMP 0x70000002 /* Timestamp */
-#define DT_MIPS_ICHECKSUM 0x70000003 /* Checksum */
-#define DT_MIPS_IVERSION 0x70000004 /* Version string (string tbl index) */
-#define DT_MIPS_FLAGS 0x70000005 /* Flags */
-#define DT_MIPS_BASE_ADDRESS 0x70000006 /* Base address */
-#define DT_MIPS_MSYM 0x70000007
-#define DT_MIPS_CONFLICT 0x70000008 /* Address of CONFLICT section */
-#define DT_MIPS_LIBLIST 0x70000009 /* Address of LIBLIST section */
-#define DT_MIPS_LOCAL_GOTNO 0x7000000a /* Number of local GOT entries */
-#define DT_MIPS_CONFLICTNO 0x7000000b /* Number of CONFLICT entries */
-#define DT_MIPS_LIBLISTNO 0x70000010 /* Number of LIBLIST entries */
-#define DT_MIPS_SYMTABNO 0x70000011 /* Number of DYNSYM entries */
-#define DT_MIPS_UNREFEXTNO 0x70000012 /* First external DYNSYM */
-#define DT_MIPS_GOTSYM 0x70000013 /* First GOT entry in DYNSYM */
-#define DT_MIPS_HIPAGENO 0x70000014 /* Number of GOT page table entries */
-#define DT_MIPS_RLD_MAP 0x70000016 /* Address of run time loader map. */
-#define DT_MIPS_DELTA_CLASS 0x70000017 /* Delta C++ class definition. */
-#define DT_MIPS_DELTA_CLASS_NO 0x70000018 /* Number of entries in
- DT_MIPS_DELTA_CLASS. */
-#define DT_MIPS_DELTA_INSTANCE 0x70000019 /* Delta C++ class instances. */
-#define DT_MIPS_DELTA_INSTANCE_NO 0x7000001a /* Number of entries in
- DT_MIPS_DELTA_INSTANCE. */
-#define DT_MIPS_DELTA_RELOC 0x7000001b /* Delta relocations. */
-#define DT_MIPS_DELTA_RELOC_NO 0x7000001c /* Number of entries in
- DT_MIPS_DELTA_RELOC. */
-#define DT_MIPS_DELTA_SYM 0x7000001d /* Delta symbols that Delta
- relocations refer to. */
-#define DT_MIPS_DELTA_SYM_NO 0x7000001e /* Number of entries in
- DT_MIPS_DELTA_SYM. */
-#define DT_MIPS_DELTA_CLASSSYM 0x70000020 /* Delta symbols that hold the
- class declaration. */
-#define DT_MIPS_DELTA_CLASSSYM_NO 0x70000021 /* Number of entries in
- DT_MIPS_DELTA_CLASSSYM. */
-#define DT_MIPS_CXX_FLAGS 0x70000022 /* Flags indicating for C++ flavor. */
-#define DT_MIPS_PIXIE_INIT 0x70000023
-#define DT_MIPS_SYMBOL_LIB 0x70000024
-#define DT_MIPS_LOCALPAGE_GOTIDX 0x70000025
-#define DT_MIPS_LOCAL_GOTIDX 0x70000026
-#define DT_MIPS_HIDDEN_GOTIDX 0x70000027
-#define DT_MIPS_PROTECTED_GOTIDX 0x70000028
-#define DT_MIPS_OPTIONS 0x70000029 /* Address of .options. */
-#define DT_MIPS_INTERFACE 0x7000002a /* Address of .interface. */
-#define DT_MIPS_DYNSTR_ALIGN 0x7000002b
-#define DT_MIPS_INTERFACE_SIZE 0x7000002c /* Size of the .interface section. */
-#define DT_MIPS_RLD_TEXT_RESOLVE_ADDR 0x7000002d /* Address of rld_text_rsolve
- function stored in GOT. */
-#define DT_MIPS_PERF_SUFFIX 0x7000002e /* Default suffix of dso to be added
- by rld on dlopen() calls. */
-#define DT_MIPS_COMPACT_SIZE 0x7000002f /* (O32)Size of compact rel section. */
-#define DT_MIPS_GP_VALUE 0x70000030 /* GP value for aux GOTs. */
-#define DT_MIPS_AUX_DYNAMIC 0x70000031 /* Address of aux .dynamic. */
-/* The address of .got.plt in an executable using the new non-PIC ABI. */
-#define DT_MIPS_PLTGOT 0x70000032
-/* The base of the PLT in an executable using the new non-PIC ABI if that
- PLT is writable. For a non-writable PLT, this is omitted or has a zero
- value. */
-#define DT_MIPS_RWPLT 0x70000034
-/* An alternative description of the classic MIPS RLD_MAP that is usable
- in a PIE as it stores a relative offset from the address of the tag
- rather than an absolute address. */
-#define DT_MIPS_RLD_MAP_REL 0x70000035
-#define DT_MIPS_NUM 0x36
-
-/* Legal values for DT_MIPS_FLAGS Elf32_Dyn entry. */
-
-#define RHF_NONE 0 /* No flags */
-#define RHF_QUICKSTART (1 << 0) /* Use quickstart */
-#define RHF_NOTPOT (1 << 1) /* Hash size not power of 2 */
-#define RHF_NO_LIBRARY_REPLACEMENT (1 << 2) /* Ignore LD_LIBRARY_PATH */
-#define RHF_NO_MOVE (1 << 3)
-#define RHF_SGI_ONLY (1 << 4)
-#define RHF_GUARANTEE_INIT (1 << 5)
-#define RHF_DELTA_C_PLUS_PLUS (1 << 6)
-#define RHF_GUARANTEE_START_INIT (1 << 7)
-#define RHF_PIXIE (1 << 8)
-#define RHF_DEFAULT_DELAY_LOAD (1 << 9)
-#define RHF_REQUICKSTART (1 << 10)
-#define RHF_REQUICKSTARTED (1 << 11)
-#define RHF_CORD (1 << 12)
-#define RHF_NO_UNRES_UNDEF (1 << 13)
-#define RHF_RLD_ORDER_SAFE (1 << 14)
-
-/* Entries found in sections of type SHT_MIPS_LIBLIST. */
-
-typedef struct
-{
- Elf32_Word l_name; /* Name (string table index) */
- Elf32_Word l_time_stamp; /* Timestamp */
- Elf32_Word l_checksum; /* Checksum */
- Elf32_Word l_version; /* Interface version */
- Elf32_Word l_flags; /* Flags */
-} Elf32_Lib;
-
-typedef struct
-{
- Elf64_Word l_name; /* Name (string table index) */
- Elf64_Word l_time_stamp; /* Timestamp */
- Elf64_Word l_checksum; /* Checksum */
- Elf64_Word l_version; /* Interface version */
- Elf64_Word l_flags; /* Flags */
-} Elf64_Lib;
-
-
-/* Legal values for l_flags. */
-
-#define LL_NONE 0
-#define LL_EXACT_MATCH (1 << 0) /* Require exact match */
-#define LL_IGNORE_INT_VER (1 << 1) /* Ignore interface version */
-#define LL_REQUIRE_MINOR (1 << 2)
-#define LL_EXPORTS (1 << 3)
-#define LL_DELAY_LOAD (1 << 4)
-#define LL_DELTA (1 << 5)
-
-/* Entries found in sections of type SHT_MIPS_CONFLICT. */
-
-typedef Elf32_Addr Elf32_Conflict;
-
-typedef struct
-{
- /* Version of flags structure. */
- Elf32_Half version;
- /* The level of the ISA: 1-5, 32, 64. */
- unsigned char isa_level;
- /* The revision of ISA: 0 for MIPS V and below, 1-n otherwise. */
- unsigned char isa_rev;
- /* The size of general purpose registers. */
- unsigned char gpr_size;
- /* The size of co-processor 1 registers. */
- unsigned char cpr1_size;
- /* The size of co-processor 2 registers. */
- unsigned char cpr2_size;
- /* The floating-point ABI. */
- unsigned char fp_abi;
- /* Processor-specific extension. */
- Elf32_Word isa_ext;
- /* Mask of ASEs used. */
- Elf32_Word ases;
- /* Mask of general flags. */
- Elf32_Word flags1;
- Elf32_Word flags2;
-} Elf_MIPS_ABIFlags_v0;
-
-/* Values for the register size bytes of an abi flags structure. */
-
-#define MIPS_AFL_REG_NONE 0x00 /* No registers. */
-#define MIPS_AFL_REG_32 0x01 /* 32-bit registers. */
-#define MIPS_AFL_REG_64 0x02 /* 64-bit registers. */
-#define MIPS_AFL_REG_128 0x03 /* 128-bit registers. */
-
-/* Masks for the ases word of an ABI flags structure. */
-
-#define MIPS_AFL_ASE_DSP 0x00000001 /* DSP ASE. */
-#define MIPS_AFL_ASE_DSPR2 0x00000002 /* DSP R2 ASE. */
-#define MIPS_AFL_ASE_EVA 0x00000004 /* Enhanced VA Scheme. */
-#define MIPS_AFL_ASE_MCU 0x00000008 /* MCU (MicroController) ASE. */
-#define MIPS_AFL_ASE_MDMX 0x00000010 /* MDMX ASE. */
-#define MIPS_AFL_ASE_MIPS3D 0x00000020 /* MIPS-3D ASE. */
-#define MIPS_AFL_ASE_MT 0x00000040 /* MT ASE. */
-#define MIPS_AFL_ASE_SMARTMIPS 0x00000080 /* SmartMIPS ASE. */
-#define MIPS_AFL_ASE_VIRT 0x00000100 /* VZ ASE. */
-#define MIPS_AFL_ASE_MSA 0x00000200 /* MSA ASE. */
-#define MIPS_AFL_ASE_MIPS16 0x00000400 /* MIPS16 ASE. */
-#define MIPS_AFL_ASE_MICROMIPS 0x00000800 /* MICROMIPS ASE. */
-#define MIPS_AFL_ASE_XPA 0x00001000 /* XPA ASE. */
-#define MIPS_AFL_ASE_MASK 0x00001fff /* All ASEs. */
-
-/* Values for the isa_ext word of an ABI flags structure. */
-
-#define MIPS_AFL_EXT_XLR 1 /* RMI Xlr instruction. */
-#define MIPS_AFL_EXT_OCTEON2 2 /* Cavium Networks Octeon2. */
-#define MIPS_AFL_EXT_OCTEONP 3 /* Cavium Networks OcteonP. */
-#define MIPS_AFL_EXT_LOONGSON_3A 4 /* Loongson 3A. */
-#define MIPS_AFL_EXT_OCTEON 5 /* Cavium Networks Octeon. */
-#define MIPS_AFL_EXT_5900 6 /* MIPS R5900 instruction. */
-#define MIPS_AFL_EXT_4650 7 /* MIPS R4650 instruction. */
-#define MIPS_AFL_EXT_4010 8 /* LSI R4010 instruction. */
-#define MIPS_AFL_EXT_4100 9 /* NEC VR4100 instruction. */
-#define MIPS_AFL_EXT_3900 10 /* Toshiba R3900 instruction. */
-#define MIPS_AFL_EXT_10000 11 /* MIPS R10000 instruction. */
-#define MIPS_AFL_EXT_SB1 12 /* Broadcom SB-1 instruction. */
-#define MIPS_AFL_EXT_4111 13 /* NEC VR4111/VR4181 instruction. */
-#define MIPS_AFL_EXT_4120 14 /* NEC VR4120 instruction. */
-#define MIPS_AFL_EXT_5400 15 /* NEC VR5400 instruction. */
-#define MIPS_AFL_EXT_5500 16 /* NEC VR5500 instruction. */
-#define MIPS_AFL_EXT_LOONGSON_2E 17 /* ST Microelectronics Loongson 2E. */
-#define MIPS_AFL_EXT_LOONGSON_2F 18 /* ST Microelectronics Loongson 2F. */
-
-/* Masks for the flags1 word of an ABI flags structure. */
-#define MIPS_AFL_FLAGS1_ODDSPREG 1 /* Uses odd single-precision registers. */
-
-/* Object attribute values. */
-enum
-{
- /* Not tagged or not using any ABIs affected by the differences. */
- Val_GNU_MIPS_ABI_FP_ANY = 0,
- /* Using hard-float -mdouble-float. */
- Val_GNU_MIPS_ABI_FP_DOUBLE = 1,
- /* Using hard-float -msingle-float. */
- Val_GNU_MIPS_ABI_FP_SINGLE = 2,
- /* Using soft-float. */
- Val_GNU_MIPS_ABI_FP_SOFT = 3,
- /* Using -mips32r2 -mfp64. */
- Val_GNU_MIPS_ABI_FP_OLD_64 = 4,
- /* Using -mfpxx. */
- Val_GNU_MIPS_ABI_FP_XX = 5,
- /* Using -mips32r2 -mfp64. */
- Val_GNU_MIPS_ABI_FP_64 = 6,
- /* Using -mips32r2 -mfp64 -mno-odd-spreg. */
- Val_GNU_MIPS_ABI_FP_64A = 7,
- /* Maximum allocated FP ABI value. */
- Val_GNU_MIPS_ABI_FP_MAX = 7
-};
-
-/* HPPA specific definitions. */
-
-/* Legal values for e_flags field of Elf32_Ehdr. */
-
-#define EF_PARISC_TRAPNIL 0x00010000 /* Trap nil pointer dereference. */
-#define EF_PARISC_EXT 0x00020000 /* Program uses arch. extensions. */
-#define EF_PARISC_LSB 0x00040000 /* Program expects little endian. */
-#define EF_PARISC_WIDE 0x00080000 /* Program expects wide mode. */
-#define EF_PARISC_NO_KABP 0x00100000 /* No kernel assisted branch
- prediction. */
-#define EF_PARISC_LAZYSWAP 0x00400000 /* Allow lazy swapping. */
-#define EF_PARISC_ARCH 0x0000ffff /* Architecture version. */
-
-/* Defined values for `e_flags & EF_PARISC_ARCH' are: */
-
-#define EFA_PARISC_1_0 0x020b /* PA-RISC 1.0 big-endian. */
-#define EFA_PARISC_1_1 0x0210 /* PA-RISC 1.1 big-endian. */
-#define EFA_PARISC_2_0 0x0214 /* PA-RISC 2.0 big-endian. */
-
-/* Additional section indeces. */
-
-#define SHN_PARISC_ANSI_COMMON 0xff00 /* Section for tenatively declared
- symbols in ANSI C. */
-#define SHN_PARISC_HUGE_COMMON 0xff01 /* Common blocks in huge model. */
-
-/* Legal values for sh_type field of Elf32_Shdr. */
-
-#define SHT_PARISC_EXT 0x70000000 /* Contains product specific ext. */
-#define SHT_PARISC_UNWIND 0x70000001 /* Unwind information. */
-#define SHT_PARISC_DOC 0x70000002 /* Debug info for optimized code. */
-
-/* Legal values for sh_flags field of Elf32_Shdr. */
-
-#define SHF_PARISC_SHORT 0x20000000 /* Section with short addressing. */
-#define SHF_PARISC_HUGE 0x40000000 /* Section far from gp. */
-#define SHF_PARISC_SBP 0x80000000 /* Static branch prediction code. */
-
-/* Legal values for ST_TYPE subfield of st_info (symbol type). */
-
-#define STT_PARISC_MILLICODE 13 /* Millicode function entry point. */
-
-#define STT_HP_OPAQUE (STT_LOOS + 0x1)
-#define STT_HP_STUB (STT_LOOS + 0x2)
-
-/* HPPA relocs. */
-
-#define R_PARISC_NONE 0 /* No reloc. */
-#define R_PARISC_DIR32 1 /* Direct 32-bit reference. */
-#define R_PARISC_DIR21L 2 /* Left 21 bits of eff. address. */
-#define R_PARISC_DIR17R 3 /* Right 17 bits of eff. address. */
-#define R_PARISC_DIR17F 4 /* 17 bits of eff. address. */
-#define R_PARISC_DIR14R 6 /* Right 14 bits of eff. address. */
-#define R_PARISC_PCREL32 9 /* 32-bit rel. address. */
-#define R_PARISC_PCREL21L 10 /* Left 21 bits of rel. address. */
-#define R_PARISC_PCREL17R 11 /* Right 17 bits of rel. address. */
-#define R_PARISC_PCREL17F 12 /* 17 bits of rel. address. */
-#define R_PARISC_PCREL14R 14 /* Right 14 bits of rel. address. */
-#define R_PARISC_DPREL21L 18 /* Left 21 bits of rel. address. */
-#define R_PARISC_DPREL14R 22 /* Right 14 bits of rel. address. */
-#define R_PARISC_GPREL21L 26 /* GP-relative, left 21 bits. */
-#define R_PARISC_GPREL14R 30 /* GP-relative, right 14 bits. */
-#define R_PARISC_LTOFF21L 34 /* LT-relative, left 21 bits. */
-#define R_PARISC_LTOFF14R 38 /* LT-relative, right 14 bits. */
-#define R_PARISC_SECREL32 41 /* 32 bits section rel. address. */
-#define R_PARISC_SEGBASE 48 /* No relocation, set segment base. */
-#define R_PARISC_SEGREL32 49 /* 32 bits segment rel. address. */
-#define R_PARISC_PLTOFF21L 50 /* PLT rel. address, left 21 bits. */
-#define R_PARISC_PLTOFF14R 54 /* PLT rel. address, right 14 bits. */
-#define R_PARISC_LTOFF_FPTR32 57 /* 32 bits LT-rel. function pointer. */
-#define R_PARISC_LTOFF_FPTR21L 58 /* LT-rel. fct ptr, left 21 bits. */
-#define R_PARISC_LTOFF_FPTR14R 62 /* LT-rel. fct ptr, right 14 bits. */
-#define R_PARISC_FPTR64 64 /* 64 bits function address. */
-#define R_PARISC_PLABEL32 65 /* 32 bits function address. */
-#define R_PARISC_PLABEL21L 66 /* Left 21 bits of fdesc address. */
-#define R_PARISC_PLABEL14R 70 /* Right 14 bits of fdesc address. */
-#define R_PARISC_PCREL64 72 /* 64 bits PC-rel. address. */
-#define R_PARISC_PCREL22F 74 /* 22 bits PC-rel. address. */
-#define R_PARISC_PCREL14WR 75 /* PC-rel. address, right 14 bits. */
-#define R_PARISC_PCREL14DR 76 /* PC rel. address, right 14 bits. */
-#define R_PARISC_PCREL16F 77 /* 16 bits PC-rel. address. */
-#define R_PARISC_PCREL16WF 78 /* 16 bits PC-rel. address. */
-#define R_PARISC_PCREL16DF 79 /* 16 bits PC-rel. address. */
-#define R_PARISC_DIR64 80 /* 64 bits of eff. address. */
-#define R_PARISC_DIR14WR 83 /* 14 bits of eff. address. */
-#define R_PARISC_DIR14DR 84 /* 14 bits of eff. address. */
-#define R_PARISC_DIR16F 85 /* 16 bits of eff. address. */
-#define R_PARISC_DIR16WF 86 /* 16 bits of eff. address. */
-#define R_PARISC_DIR16DF 87 /* 16 bits of eff. address. */
-#define R_PARISC_GPREL64 88 /* 64 bits of GP-rel. address. */
-#define R_PARISC_GPREL14WR 91 /* GP-rel. address, right 14 bits. */
-#define R_PARISC_GPREL14DR 92 /* GP-rel. address, right 14 bits. */
-#define R_PARISC_GPREL16F 93 /* 16 bits GP-rel. address. */
-#define R_PARISC_GPREL16WF 94 /* 16 bits GP-rel. address. */
-#define R_PARISC_GPREL16DF 95 /* 16 bits GP-rel. address. */
-#define R_PARISC_LTOFF64 96 /* 64 bits LT-rel. address. */
-#define R_PARISC_LTOFF14WR 99 /* LT-rel. address, right 14 bits. */
-#define R_PARISC_LTOFF14DR 100 /* LT-rel. address, right 14 bits. */
-#define R_PARISC_LTOFF16F 101 /* 16 bits LT-rel. address. */
-#define R_PARISC_LTOFF16WF 102 /* 16 bits LT-rel. address. */
-#define R_PARISC_LTOFF16DF 103 /* 16 bits LT-rel. address. */
-#define R_PARISC_SECREL64 104 /* 64 bits section rel. address. */
-#define R_PARISC_SEGREL64 112 /* 64 bits segment rel. address. */
-#define R_PARISC_PLTOFF14WR 115 /* PLT-rel. address, right 14 bits. */
-#define R_PARISC_PLTOFF14DR 116 /* PLT-rel. address, right 14 bits. */
-#define R_PARISC_PLTOFF16F 117 /* 16 bits LT-rel. address. */
-#define R_PARISC_PLTOFF16WF 118 /* 16 bits PLT-rel. address. */
-#define R_PARISC_PLTOFF16DF 119 /* 16 bits PLT-rel. address. */
-#define R_PARISC_LTOFF_FPTR64 120 /* 64 bits LT-rel. function ptr. */
-#define R_PARISC_LTOFF_FPTR14WR 123 /* LT-rel. fct. ptr., right 14 bits. */
-#define R_PARISC_LTOFF_FPTR14DR 124 /* LT-rel. fct. ptr., right 14 bits. */
-#define R_PARISC_LTOFF_FPTR16F 125 /* 16 bits LT-rel. function ptr. */
-#define R_PARISC_LTOFF_FPTR16WF 126 /* 16 bits LT-rel. function ptr. */
-#define R_PARISC_LTOFF_FPTR16DF 127 /* 16 bits LT-rel. function ptr. */
-#define R_PARISC_LORESERVE 128
-#define R_PARISC_COPY 128 /* Copy relocation. */
-#define R_PARISC_IPLT 129 /* Dynamic reloc, imported PLT */
-#define R_PARISC_EPLT 130 /* Dynamic reloc, exported PLT */
-#define R_PARISC_TPREL32 153 /* 32 bits TP-rel. address. */
-#define R_PARISC_TPREL21L 154 /* TP-rel. address, left 21 bits. */
-#define R_PARISC_TPREL14R 158 /* TP-rel. address, right 14 bits. */
-#define R_PARISC_LTOFF_TP21L 162 /* LT-TP-rel. address, left 21 bits. */
-#define R_PARISC_LTOFF_TP14R 166 /* LT-TP-rel. address, right 14 bits.*/
-#define R_PARISC_LTOFF_TP14F 167 /* 14 bits LT-TP-rel. address. */
-#define R_PARISC_TPREL64 216 /* 64 bits TP-rel. address. */
-#define R_PARISC_TPREL14WR 219 /* TP-rel. address, right 14 bits. */
-#define R_PARISC_TPREL14DR 220 /* TP-rel. address, right 14 bits. */
-#define R_PARISC_TPREL16F 221 /* 16 bits TP-rel. address. */
-#define R_PARISC_TPREL16WF 222 /* 16 bits TP-rel. address. */
-#define R_PARISC_TPREL16DF 223 /* 16 bits TP-rel. address. */
-#define R_PARISC_LTOFF_TP64 224 /* 64 bits LT-TP-rel. address. */
-#define R_PARISC_LTOFF_TP14WR 227 /* LT-TP-rel. address, right 14 bits.*/
-#define R_PARISC_LTOFF_TP14DR 228 /* LT-TP-rel. address, right 14 bits.*/
-#define R_PARISC_LTOFF_TP16F 229 /* 16 bits LT-TP-rel. address. */
-#define R_PARISC_LTOFF_TP16WF 230 /* 16 bits LT-TP-rel. address. */
-#define R_PARISC_LTOFF_TP16DF 231 /* 16 bits LT-TP-rel. address. */
-#define R_PARISC_GNU_VTENTRY 232
-#define R_PARISC_GNU_VTINHERIT 233
-#define R_PARISC_TLS_GD21L 234 /* GD 21-bit left. */
-#define R_PARISC_TLS_GD14R 235 /* GD 14-bit right. */
-#define R_PARISC_TLS_GDCALL 236 /* GD call to __t_g_a. */
-#define R_PARISC_TLS_LDM21L 237 /* LD module 21-bit left. */
-#define R_PARISC_TLS_LDM14R 238 /* LD module 14-bit right. */
-#define R_PARISC_TLS_LDMCALL 239 /* LD module call to __t_g_a. */
-#define R_PARISC_TLS_LDO21L 240 /* LD offset 21-bit left. */
-#define R_PARISC_TLS_LDO14R 241 /* LD offset 14-bit right. */
-#define R_PARISC_TLS_DTPMOD32 242 /* DTP module 32-bit. */
-#define R_PARISC_TLS_DTPMOD64 243 /* DTP module 64-bit. */
-#define R_PARISC_TLS_DTPOFF32 244 /* DTP offset 32-bit. */
-#define R_PARISC_TLS_DTPOFF64 245 /* DTP offset 32-bit. */
-#define R_PARISC_TLS_LE21L R_PARISC_TPREL21L
-#define R_PARISC_TLS_LE14R R_PARISC_TPREL14R
-#define R_PARISC_TLS_IE21L R_PARISC_LTOFF_TP21L
-#define R_PARISC_TLS_IE14R R_PARISC_LTOFF_TP14R
-#define R_PARISC_TLS_TPREL32 R_PARISC_TPREL32
-#define R_PARISC_TLS_TPREL64 R_PARISC_TPREL64
-#define R_PARISC_HIRESERVE 255
-
-/* Legal values for p_type field of Elf32_Phdr/Elf64_Phdr. */
-
-#define PT_HP_TLS (PT_LOOS + 0x0)
-#define PT_HP_CORE_NONE (PT_LOOS + 0x1)
-#define PT_HP_CORE_VERSION (PT_LOOS + 0x2)
-#define PT_HP_CORE_KERNEL (PT_LOOS + 0x3)
-#define PT_HP_CORE_COMM (PT_LOOS + 0x4)
-#define PT_HP_CORE_PROC (PT_LOOS + 0x5)
-#define PT_HP_CORE_LOADABLE (PT_LOOS + 0x6)
-#define PT_HP_CORE_STACK (PT_LOOS + 0x7)
-#define PT_HP_CORE_SHM (PT_LOOS + 0x8)
-#define PT_HP_CORE_MMF (PT_LOOS + 0x9)
-#define PT_HP_PARALLEL (PT_LOOS + 0x10)
-#define PT_HP_FASTBIND (PT_LOOS + 0x11)
-#define PT_HP_OPT_ANNOT (PT_LOOS + 0x12)
-#define PT_HP_HSL_ANNOT (PT_LOOS + 0x13)
-#define PT_HP_STACK (PT_LOOS + 0x14)
-
-#define PT_PARISC_ARCHEXT 0x70000000
-#define PT_PARISC_UNWIND 0x70000001
-
-/* Legal values for p_flags field of Elf32_Phdr/Elf64_Phdr. */
-
-#define PF_PARISC_SBP 0x08000000
-
-#define PF_HP_PAGE_SIZE 0x00100000
-#define PF_HP_FAR_SHARED 0x00200000
-#define PF_HP_NEAR_SHARED 0x00400000
-#define PF_HP_CODE 0x01000000
-#define PF_HP_MODIFY 0x02000000
-#define PF_HP_LAZYSWAP 0x04000000
-#define PF_HP_SBP 0x08000000
-
-
-/* Alpha specific definitions. */
-
-/* Legal values for e_flags field of Elf64_Ehdr. */
-
-#define EF_ALPHA_32BIT 1 /* All addresses must be < 2GB. */
-#define EF_ALPHA_CANRELAX 2 /* Relocations for relaxing exist. */
-
-/* Legal values for sh_type field of Elf64_Shdr. */
-
-/* These two are primerily concerned with ECOFF debugging info. */
-#define SHT_ALPHA_DEBUG 0x70000001
-#define SHT_ALPHA_REGINFO 0x70000002
-
-/* Legal values for sh_flags field of Elf64_Shdr. */
-
-#define SHF_ALPHA_GPREL 0x10000000
-
-/* Legal values for st_other field of Elf64_Sym. */
-#define STO_ALPHA_NOPV 0x80 /* No PV required. */
-#define STO_ALPHA_STD_GPLOAD 0x88 /* PV only used for initial ldgp. */
-
-/* Alpha relocs. */
-
-#define R_ALPHA_NONE 0 /* No reloc */
-#define R_ALPHA_REFLONG 1 /* Direct 32 bit */
-#define R_ALPHA_REFQUAD 2 /* Direct 64 bit */
-#define R_ALPHA_GPREL32 3 /* GP relative 32 bit */
-#define R_ALPHA_LITERAL 4 /* GP relative 16 bit w/optimization */
-#define R_ALPHA_LITUSE 5 /* Optimization hint for LITERAL */
-#define R_ALPHA_GPDISP 6 /* Add displacement to GP */
-#define R_ALPHA_BRADDR 7 /* PC+4 relative 23 bit shifted */
-#define R_ALPHA_HINT 8 /* PC+4 relative 16 bit shifted */
-#define R_ALPHA_SREL16 9 /* PC relative 16 bit */
-#define R_ALPHA_SREL32 10 /* PC relative 32 bit */
-#define R_ALPHA_SREL64 11 /* PC relative 64 bit */
-#define R_ALPHA_GPRELHIGH 17 /* GP relative 32 bit, high 16 bits */
-#define R_ALPHA_GPRELLOW 18 /* GP relative 32 bit, low 16 bits */
-#define R_ALPHA_GPREL16 19 /* GP relative 16 bit */
-#define R_ALPHA_COPY 24 /* Copy symbol at runtime */
-#define R_ALPHA_GLOB_DAT 25 /* Create GOT entry */
-#define R_ALPHA_JMP_SLOT 26 /* Create PLT entry */
-#define R_ALPHA_RELATIVE 27 /* Adjust by program base */
-#define R_ALPHA_TLS_GD_HI 28
-#define R_ALPHA_TLSGD 29
-#define R_ALPHA_TLS_LDM 30
-#define R_ALPHA_DTPMOD64 31
-#define R_ALPHA_GOTDTPREL 32
-#define R_ALPHA_DTPREL64 33
-#define R_ALPHA_DTPRELHI 34
-#define R_ALPHA_DTPRELLO 35
-#define R_ALPHA_DTPREL16 36
-#define R_ALPHA_GOTTPREL 37
-#define R_ALPHA_TPREL64 38
-#define R_ALPHA_TPRELHI 39
-#define R_ALPHA_TPRELLO 40
-#define R_ALPHA_TPREL16 41
-/* Keep this the last entry. */
-#define R_ALPHA_NUM 46
-
-/* Magic values of the LITUSE relocation addend. */
-#define LITUSE_ALPHA_ADDR 0
-#define LITUSE_ALPHA_BASE 1
-#define LITUSE_ALPHA_BYTOFF 2
-#define LITUSE_ALPHA_JSR 3
-#define LITUSE_ALPHA_TLS_GD 4
-#define LITUSE_ALPHA_TLS_LDM 5
-
-/* Legal values for d_tag of Elf64_Dyn. */
-#define DT_ALPHA_PLTRO (DT_LOPROC + 0)
-#define DT_ALPHA_NUM 1
-
-/* PowerPC specific declarations */
-
-/* Values for Elf32/64_Ehdr.e_flags. */
-#define EF_PPC_EMB 0x80000000 /* PowerPC embedded flag */
-
-/* Cygnus local bits below */
-#define EF_PPC_RELOCATABLE 0x00010000 /* PowerPC -mrelocatable flag*/
-#define EF_PPC_RELOCATABLE_LIB 0x00008000 /* PowerPC -mrelocatable-lib
- flag */
-
-/* PowerPC relocations defined by the ABIs */
-#define R_PPC_NONE 0
-#define R_PPC_ADDR32 1 /* 32bit absolute address */
-#define R_PPC_ADDR24 2 /* 26bit address, 2 bits ignored. */
-#define R_PPC_ADDR16 3 /* 16bit absolute address */
-#define R_PPC_ADDR16_LO 4 /* lower 16bit of absolute address */
-#define R_PPC_ADDR16_HI 5 /* high 16bit of absolute address */
-#define R_PPC_ADDR16_HA 6 /* adjusted high 16bit */
-#define R_PPC_ADDR14 7 /* 16bit address, 2 bits ignored */
-#define R_PPC_ADDR14_BRTAKEN 8
-#define R_PPC_ADDR14_BRNTAKEN 9
-#define R_PPC_REL24 10 /* PC relative 26 bit */
-#define R_PPC_REL14 11 /* PC relative 16 bit */
-#define R_PPC_REL14_BRTAKEN 12
-#define R_PPC_REL14_BRNTAKEN 13
-#define R_PPC_GOT16 14
-#define R_PPC_GOT16_LO 15
-#define R_PPC_GOT16_HI 16
-#define R_PPC_GOT16_HA 17
-#define R_PPC_PLTREL24 18
-#define R_PPC_COPY 19
-#define R_PPC_GLOB_DAT 20
-#define R_PPC_JMP_SLOT 21
-#define R_PPC_RELATIVE 22
-#define R_PPC_LOCAL24PC 23
-#define R_PPC_UADDR32 24
-#define R_PPC_UADDR16 25
-#define R_PPC_REL32 26
-#define R_PPC_PLT32 27
-#define R_PPC_PLTREL32 28
-#define R_PPC_PLT16_LO 29
-#define R_PPC_PLT16_HI 30
-#define R_PPC_PLT16_HA 31
-#define R_PPC_SDAREL16 32
-#define R_PPC_SECTOFF 33
-#define R_PPC_SECTOFF_LO 34
-#define R_PPC_SECTOFF_HI 35
-#define R_PPC_SECTOFF_HA 36
-
-/* PowerPC relocations defined for the TLS access ABI. */
-#define R_PPC_TLS 67 /* none (sym+add)@tls */
-#define R_PPC_DTPMOD32 68 /* word32 (sym+add)@dtpmod */
-#define R_PPC_TPREL16 69 /* half16* (sym+add)@tprel */
-#define R_PPC_TPREL16_LO 70 /* half16 (sym+add)@tprel@l */
-#define R_PPC_TPREL16_HI 71 /* half16 (sym+add)@tprel@h */
-#define R_PPC_TPREL16_HA 72 /* half16 (sym+add)@tprel@ha */
-#define R_PPC_TPREL32 73 /* word32 (sym+add)@tprel */
-#define R_PPC_DTPREL16 74 /* half16* (sym+add)@dtprel */
-#define R_PPC_DTPREL16_LO 75 /* half16 (sym+add)@dtprel@l */
-#define R_PPC_DTPREL16_HI 76 /* half16 (sym+add)@dtprel@h */
-#define R_PPC_DTPREL16_HA 77 /* half16 (sym+add)@dtprel@ha */
-#define R_PPC_DTPREL32 78 /* word32 (sym+add)@dtprel */
-#define R_PPC_GOT_TLSGD16 79 /* half16* (sym+add)@got@tlsgd */
-#define R_PPC_GOT_TLSGD16_LO 80 /* half16 (sym+add)@got@tlsgd@l */
-#define R_PPC_GOT_TLSGD16_HI 81 /* half16 (sym+add)@got@tlsgd@h */
-#define R_PPC_GOT_TLSGD16_HA 82 /* half16 (sym+add)@got@tlsgd@ha */
-#define R_PPC_GOT_TLSLD16 83 /* half16* (sym+add)@got@tlsld */
-#define R_PPC_GOT_TLSLD16_LO 84 /* half16 (sym+add)@got@tlsld@l */
-#define R_PPC_GOT_TLSLD16_HI 85 /* half16 (sym+add)@got@tlsld@h */
-#define R_PPC_GOT_TLSLD16_HA 86 /* half16 (sym+add)@got@tlsld@ha */
-#define R_PPC_GOT_TPREL16 87 /* half16* (sym+add)@got@tprel */
-#define R_PPC_GOT_TPREL16_LO 88 /* half16 (sym+add)@got@tprel@l */
-#define R_PPC_GOT_TPREL16_HI 89 /* half16 (sym+add)@got@tprel@h */
-#define R_PPC_GOT_TPREL16_HA 90 /* half16 (sym+add)@got@tprel@ha */
-#define R_PPC_GOT_DTPREL16 91 /* half16* (sym+add)@got@dtprel */
-#define R_PPC_GOT_DTPREL16_LO 92 /* half16* (sym+add)@got@dtprel@l */
-#define R_PPC_GOT_DTPREL16_HI 93 /* half16* (sym+add)@got@dtprel@h */
-#define R_PPC_GOT_DTPREL16_HA 94 /* half16* (sym+add)@got@dtprel@ha */
-#define R_PPC_TLSGD 95 /* none (sym+add)@tlsgd */
-#define R_PPC_TLSLD 96 /* none (sym+add)@tlsld */
-
-/* The remaining relocs are from the Embedded ELF ABI, and are not
- in the SVR4 ELF ABI. */
-#define R_PPC_EMB_NADDR32 101
-#define R_PPC_EMB_NADDR16 102
-#define R_PPC_EMB_NADDR16_LO 103
-#define R_PPC_EMB_NADDR16_HI 104
-#define R_PPC_EMB_NADDR16_HA 105
-#define R_PPC_EMB_SDAI16 106
-#define R_PPC_EMB_SDA2I16 107
-#define R_PPC_EMB_SDA2REL 108
-#define R_PPC_EMB_SDA21 109 /* 16 bit offset in SDA */
-#define R_PPC_EMB_MRKREF 110
-#define R_PPC_EMB_RELSEC16 111
-#define R_PPC_EMB_RELST_LO 112
-#define R_PPC_EMB_RELST_HI 113
-#define R_PPC_EMB_RELST_HA 114
-#define R_PPC_EMB_BIT_FLD 115
-#define R_PPC_EMB_RELSDA 116 /* 16 bit relative offset in SDA */
-
-/* Diab tool relocations. */
-#define R_PPC_DIAB_SDA21_LO 180 /* like EMB_SDA21, but lower 16 bit */
-#define R_PPC_DIAB_SDA21_HI 181 /* like EMB_SDA21, but high 16 bit */
-#define R_PPC_DIAB_SDA21_HA 182 /* like EMB_SDA21, adjusted high 16 */
-#define R_PPC_DIAB_RELSDA_LO 183 /* like EMB_RELSDA, but lower 16 bit */
-#define R_PPC_DIAB_RELSDA_HI 184 /* like EMB_RELSDA, but high 16 bit */
-#define R_PPC_DIAB_RELSDA_HA 185 /* like EMB_RELSDA, adjusted high 16 */
-
-/* GNU extension to support local ifunc. */
-#define R_PPC_IRELATIVE 248
-
-/* GNU relocs used in PIC code sequences. */
-#define R_PPC_REL16 249 /* half16 (sym+add-.) */
-#define R_PPC_REL16_LO 250 /* half16 (sym+add-.)@l */
-#define R_PPC_REL16_HI 251 /* half16 (sym+add-.)@h */
-#define R_PPC_REL16_HA 252 /* half16 (sym+add-.)@ha */
-
-/* This is a phony reloc to handle any old fashioned TOC16 references
- that may still be in object files. */
-#define R_PPC_TOC16 255
-
-/* PowerPC specific values for the Dyn d_tag field. */
-#define DT_PPC_GOT (DT_LOPROC + 0)
-#define DT_PPC_OPT (DT_LOPROC + 1)
-#define DT_PPC_NUM 2
-
-/* PowerPC specific values for the DT_PPC_OPT Dyn entry. */
-#define PPC_OPT_TLS 1
-
-/* PowerPC64 relocations defined by the ABIs */
-#define R_PPC64_NONE R_PPC_NONE
-#define R_PPC64_ADDR32 R_PPC_ADDR32 /* 32bit absolute address */
-#define R_PPC64_ADDR24 R_PPC_ADDR24 /* 26bit address, word aligned */
-#define R_PPC64_ADDR16 R_PPC_ADDR16 /* 16bit absolute address */
-#define R_PPC64_ADDR16_LO R_PPC_ADDR16_LO /* lower 16bits of address */
-#define R_PPC64_ADDR16_HI R_PPC_ADDR16_HI /* high 16bits of address. */
-#define R_PPC64_ADDR16_HA R_PPC_ADDR16_HA /* adjusted high 16bits. */
-#define R_PPC64_ADDR14 R_PPC_ADDR14 /* 16bit address, word aligned */
-#define R_PPC64_ADDR14_BRTAKEN R_PPC_ADDR14_BRTAKEN
-#define R_PPC64_ADDR14_BRNTAKEN R_PPC_ADDR14_BRNTAKEN
-#define R_PPC64_REL24 R_PPC_REL24 /* PC-rel. 26 bit, word aligned */
-#define R_PPC64_REL14 R_PPC_REL14 /* PC relative 16 bit */
-#define R_PPC64_REL14_BRTAKEN R_PPC_REL14_BRTAKEN
-#define R_PPC64_REL14_BRNTAKEN R_PPC_REL14_BRNTAKEN
-#define R_PPC64_GOT16 R_PPC_GOT16
-#define R_PPC64_GOT16_LO R_PPC_GOT16_LO
-#define R_PPC64_GOT16_HI R_PPC_GOT16_HI
-#define R_PPC64_GOT16_HA R_PPC_GOT16_HA
-
-#define R_PPC64_COPY R_PPC_COPY
-#define R_PPC64_GLOB_DAT R_PPC_GLOB_DAT
-#define R_PPC64_JMP_SLOT R_PPC_JMP_SLOT
-#define R_PPC64_RELATIVE R_PPC_RELATIVE
-
-#define R_PPC64_UADDR32 R_PPC_UADDR32
-#define R_PPC64_UADDR16 R_PPC_UADDR16
-#define R_PPC64_REL32 R_PPC_REL32
-#define R_PPC64_PLT32 R_PPC_PLT32
-#define R_PPC64_PLTREL32 R_PPC_PLTREL32
-#define R_PPC64_PLT16_LO R_PPC_PLT16_LO
-#define R_PPC64_PLT16_HI R_PPC_PLT16_HI
-#define R_PPC64_PLT16_HA R_PPC_PLT16_HA
-
-#define R_PPC64_SECTOFF R_PPC_SECTOFF
-#define R_PPC64_SECTOFF_LO R_PPC_SECTOFF_LO
-#define R_PPC64_SECTOFF_HI R_PPC_SECTOFF_HI
-#define R_PPC64_SECTOFF_HA R_PPC_SECTOFF_HA
-#define R_PPC64_ADDR30 37 /* word30 (S + A - P) >> 2 */
-#define R_PPC64_ADDR64 38 /* doubleword64 S + A */
-#define R_PPC64_ADDR16_HIGHER 39 /* half16 #higher(S + A) */
-#define R_PPC64_ADDR16_HIGHERA 40 /* half16 #highera(S + A) */
-#define R_PPC64_ADDR16_HIGHEST 41 /* half16 #highest(S + A) */
-#define R_PPC64_ADDR16_HIGHESTA 42 /* half16 #highesta(S + A) */
-#define R_PPC64_UADDR64 43 /* doubleword64 S + A */
-#define R_PPC64_REL64 44 /* doubleword64 S + A - P */
-#define R_PPC64_PLT64 45 /* doubleword64 L + A */
-#define R_PPC64_PLTREL64 46 /* doubleword64 L + A - P */
-#define R_PPC64_TOC16 47 /* half16* S + A - .TOC */
-#define R_PPC64_TOC16_LO 48 /* half16 #lo(S + A - .TOC.) */
-#define R_PPC64_TOC16_HI 49 /* half16 #hi(S + A - .TOC.) */
-#define R_PPC64_TOC16_HA 50 /* half16 #ha(S + A - .TOC.) */
-#define R_PPC64_TOC 51 /* doubleword64 .TOC */
-#define R_PPC64_PLTGOT16 52 /* half16* M + A */
-#define R_PPC64_PLTGOT16_LO 53 /* half16 #lo(M + A) */
-#define R_PPC64_PLTGOT16_HI 54 /* half16 #hi(M + A) */
-#define R_PPC64_PLTGOT16_HA 55 /* half16 #ha(M + A) */
-
-#define R_PPC64_ADDR16_DS 56 /* half16ds* (S + A) >> 2 */
-#define R_PPC64_ADDR16_LO_DS 57 /* half16ds #lo(S + A) >> 2 */
-#define R_PPC64_GOT16_DS 58 /* half16ds* (G + A) >> 2 */
-#define R_PPC64_GOT16_LO_DS 59 /* half16ds #lo(G + A) >> 2 */
-#define R_PPC64_PLT16_LO_DS 60 /* half16ds #lo(L + A) >> 2 */
-#define R_PPC64_SECTOFF_DS 61 /* half16ds* (R + A) >> 2 */
-#define R_PPC64_SECTOFF_LO_DS 62 /* half16ds #lo(R + A) >> 2 */
-#define R_PPC64_TOC16_DS 63 /* half16ds* (S + A - .TOC.) >> 2 */
-#define R_PPC64_TOC16_LO_DS 64 /* half16ds #lo(S + A - .TOC.) >> 2 */
-#define R_PPC64_PLTGOT16_DS 65 /* half16ds* (M + A) >> 2 */
-#define R_PPC64_PLTGOT16_LO_DS 66 /* half16ds #lo(M + A) >> 2 */
-
-/* PowerPC64 relocations defined for the TLS access ABI. */
-#define R_PPC64_TLS 67 /* none (sym+add)@tls */
-#define R_PPC64_DTPMOD64 68 /* doubleword64 (sym+add)@dtpmod */
-#define R_PPC64_TPREL16 69 /* half16* (sym+add)@tprel */
-#define R_PPC64_TPREL16_LO 70 /* half16 (sym+add)@tprel@l */
-#define R_PPC64_TPREL16_HI 71 /* half16 (sym+add)@tprel@h */
-#define R_PPC64_TPREL16_HA 72 /* half16 (sym+add)@tprel@ha */
-#define R_PPC64_TPREL64 73 /* doubleword64 (sym+add)@tprel */
-#define R_PPC64_DTPREL16 74 /* half16* (sym+add)@dtprel */
-#define R_PPC64_DTPREL16_LO 75 /* half16 (sym+add)@dtprel@l */
-#define R_PPC64_DTPREL16_HI 76 /* half16 (sym+add)@dtprel@h */
-#define R_PPC64_DTPREL16_HA 77 /* half16 (sym+add)@dtprel@ha */
-#define R_PPC64_DTPREL64 78 /* doubleword64 (sym+add)@dtprel */
-#define R_PPC64_GOT_TLSGD16 79 /* half16* (sym+add)@got@tlsgd */
-#define R_PPC64_GOT_TLSGD16_LO 80 /* half16 (sym+add)@got@tlsgd@l */
-#define R_PPC64_GOT_TLSGD16_HI 81 /* half16 (sym+add)@got@tlsgd@h */
-#define R_PPC64_GOT_TLSGD16_HA 82 /* half16 (sym+add)@got@tlsgd@ha */
-#define R_PPC64_GOT_TLSLD16 83 /* half16* (sym+add)@got@tlsld */
-#define R_PPC64_GOT_TLSLD16_LO 84 /* half16 (sym+add)@got@tlsld@l */
-#define R_PPC64_GOT_TLSLD16_HI 85 /* half16 (sym+add)@got@tlsld@h */
-#define R_PPC64_GOT_TLSLD16_HA 86 /* half16 (sym+add)@got@tlsld@ha */
-#define R_PPC64_GOT_TPREL16_DS 87 /* half16ds* (sym+add)@got@tprel */
-#define R_PPC64_GOT_TPREL16_LO_DS 88 /* half16ds (sym+add)@got@tprel@l */
-#define R_PPC64_GOT_TPREL16_HI 89 /* half16 (sym+add)@got@tprel@h */
-#define R_PPC64_GOT_TPREL16_HA 90 /* half16 (sym+add)@got@tprel@ha */
-#define R_PPC64_GOT_DTPREL16_DS 91 /* half16ds* (sym+add)@got@dtprel */
-#define R_PPC64_GOT_DTPREL16_LO_DS 92 /* half16ds (sym+add)@got@dtprel@l */
-#define R_PPC64_GOT_DTPREL16_HI 93 /* half16 (sym+add)@got@dtprel@h */
-#define R_PPC64_GOT_DTPREL16_HA 94 /* half16 (sym+add)@got@dtprel@ha */
-#define R_PPC64_TPREL16_DS 95 /* half16ds* (sym+add)@tprel */
-#define R_PPC64_TPREL16_LO_DS 96 /* half16ds (sym+add)@tprel@l */
-#define R_PPC64_TPREL16_HIGHER 97 /* half16 (sym+add)@tprel@higher */
-#define R_PPC64_TPREL16_HIGHERA 98 /* half16 (sym+add)@tprel@highera */
-#define R_PPC64_TPREL16_HIGHEST 99 /* half16 (sym+add)@tprel@highest */
-#define R_PPC64_TPREL16_HIGHESTA 100 /* half16 (sym+add)@tprel@highesta */
-#define R_PPC64_DTPREL16_DS 101 /* half16ds* (sym+add)@dtprel */
-#define R_PPC64_DTPREL16_LO_DS 102 /* half16ds (sym+add)@dtprel@l */
-#define R_PPC64_DTPREL16_HIGHER 103 /* half16 (sym+add)@dtprel@higher */
-#define R_PPC64_DTPREL16_HIGHERA 104 /* half16 (sym+add)@dtprel@highera */
-#define R_PPC64_DTPREL16_HIGHEST 105 /* half16 (sym+add)@dtprel@highest */
-#define R_PPC64_DTPREL16_HIGHESTA 106 /* half16 (sym+add)@dtprel@highesta */
-#define R_PPC64_TLSGD 107 /* none (sym+add)@tlsgd */
-#define R_PPC64_TLSLD 108 /* none (sym+add)@tlsld */
-#define R_PPC64_TOCSAVE 109 /* none */
-
-/* Added when HA and HI relocs were changed to report overflows. */
-#define R_PPC64_ADDR16_HIGH 110
-#define R_PPC64_ADDR16_HIGHA 111
-#define R_PPC64_TPREL16_HIGH 112
-#define R_PPC64_TPREL16_HIGHA 113
-#define R_PPC64_DTPREL16_HIGH 114
-#define R_PPC64_DTPREL16_HIGHA 115
-
-/* GNU extension to support local ifunc. */
-#define R_PPC64_JMP_IREL 247
-#define R_PPC64_IRELATIVE 248
-#define R_PPC64_REL16 249 /* half16 (sym+add-.) */
-#define R_PPC64_REL16_LO 250 /* half16 (sym+add-.)@l */
-#define R_PPC64_REL16_HI 251 /* half16 (sym+add-.)@h */
-#define R_PPC64_REL16_HA 252 /* half16 (sym+add-.)@ha */
-
-/* e_flags bits specifying ABI.
- 1 for original function descriptor using ABI,
- 2 for revised ABI without function descriptors,
- 0 for unspecified or not using any features affected by the differences. */
-#define EF_PPC64_ABI 3
-
-/* PowerPC64 specific values for the Dyn d_tag field. */
-#define DT_PPC64_GLINK (DT_LOPROC + 0)
-#define DT_PPC64_OPD (DT_LOPROC + 1)
-#define DT_PPC64_OPDSZ (DT_LOPROC + 2)
-#define DT_PPC64_OPT (DT_LOPROC + 3)
-#define DT_PPC64_NUM 4
-
-/* PowerPC64 specific values for the DT_PPC64_OPT Dyn entry. */
-#define PPC64_OPT_TLS 1
-#define PPC64_OPT_MULTI_TOC 2
-
-/* PowerPC64 specific values for the Elf64_Sym st_other field. */
-#define STO_PPC64_LOCAL_BIT 5
-#define STO_PPC64_LOCAL_MASK (7 << STO_PPC64_LOCAL_BIT)
-#define PPC64_LOCAL_ENTRY_OFFSET(other) \
- (((1 << (((other) & STO_PPC64_LOCAL_MASK) >> STO_PPC64_LOCAL_BIT)) >> 2) << 2)
-
-
-/* ARM specific declarations */
-
-/* Processor specific flags for the ELF header e_flags field. */
-#define EF_ARM_RELEXEC 0x01
-#define EF_ARM_HASENTRY 0x02
-#define EF_ARM_INTERWORK 0x04
-#define EF_ARM_APCS_26 0x08
-#define EF_ARM_APCS_FLOAT 0x10
-#define EF_ARM_PIC 0x20
-#define EF_ARM_ALIGN8 0x40 /* 8-bit structure alignment is in use */
-#define EF_ARM_NEW_ABI 0x80
-#define EF_ARM_OLD_ABI 0x100
-#define EF_ARM_SOFT_FLOAT 0x200
-#define EF_ARM_VFP_FLOAT 0x400
-#define EF_ARM_MAVERICK_FLOAT 0x800
-
-#define EF_ARM_ABI_FLOAT_SOFT 0x200 /* NB conflicts with EF_ARM_SOFT_FLOAT */
-#define EF_ARM_ABI_FLOAT_HARD 0x400 /* NB conflicts with EF_ARM_VFP_FLOAT */
-
-
-/* Other constants defined in the ARM ELF spec. version B-01. */
-/* NB. These conflict with values defined above. */
-#define EF_ARM_SYMSARESORTED 0x04
-#define EF_ARM_DYNSYMSUSESEGIDX 0x08
-#define EF_ARM_MAPSYMSFIRST 0x10
-#define EF_ARM_EABIMASK 0XFF000000
-
-/* Constants defined in AAELF. */
-#define EF_ARM_BE8 0x00800000
-#define EF_ARM_LE8 0x00400000
-
-#define EF_ARM_EABI_VERSION(flags) ((flags) & EF_ARM_EABIMASK)
-#define EF_ARM_EABI_UNKNOWN 0x00000000
-#define EF_ARM_EABI_VER1 0x01000000
-#define EF_ARM_EABI_VER2 0x02000000
-#define EF_ARM_EABI_VER3 0x03000000
-#define EF_ARM_EABI_VER4 0x04000000
-#define EF_ARM_EABI_VER5 0x05000000
-
-/* Additional symbol types for Thumb. */
-#define STT_ARM_TFUNC STT_LOPROC /* A Thumb function. */
-#define STT_ARM_16BIT STT_HIPROC /* A Thumb label. */
-
-/* ARM-specific values for sh_flags */
-#define SHF_ARM_ENTRYSECT 0x10000000 /* Section contains an entry point */
-#define SHF_ARM_COMDEF 0x80000000 /* Section may be multiply defined
- in the input to a link step. */
-
-/* ARM-specific program header flags */
-#define PF_ARM_SB 0x10000000 /* Segment contains the location
- addressed by the static base. */
-#define PF_ARM_PI 0x20000000 /* Position-independent segment. */
-#define PF_ARM_ABS 0x40000000 /* Absolute segment. */
-
-/* Processor specific values for the Phdr p_type field. */
-#define PT_ARM_EXIDX (PT_LOPROC + 1) /* ARM unwind segment. */
-
-/* Processor specific values for the Shdr sh_type field. */
-#define SHT_ARM_EXIDX (SHT_LOPROC + 1) /* ARM unwind section. */
-#define SHT_ARM_PREEMPTMAP (SHT_LOPROC + 2) /* Preemption details. */
-#define SHT_ARM_ATTRIBUTES (SHT_LOPROC + 3) /* ARM attributes section. */
-
-
-/* AArch64 relocs. */
-
-#define R_AARCH64_NONE 0 /* No relocation. */
-
-/* ILP32 AArch64 relocs. */
-#define R_AARCH64_P32_ABS32 1 /* Direct 32 bit. */
-#define R_AARCH64_P32_COPY 180 /* Copy symbol at runtime. */
-#define R_AARCH64_P32_GLOB_DAT 181 /* Create GOT entry. */
-#define R_AARCH64_P32_JUMP_SLOT 182 /* Create PLT entry. */
-#define R_AARCH64_P32_RELATIVE 183 /* Adjust by program base. */
-#define R_AARCH64_P32_TLS_DTPMOD 184 /* Module number, 32 bit. */
-#define R_AARCH64_P32_TLS_DTPREL 185 /* Module-relative offset, 32 bit. */
-#define R_AARCH64_P32_TLS_TPREL 186 /* TP-relative offset, 32 bit. */
-#define R_AARCH64_P32_TLSDESC 187 /* TLS Descriptor. */
-#define R_AARCH64_P32_IRELATIVE 188 /* STT_GNU_IFUNC relocation. */
-
-/* LP64 AArch64 relocs. */
-#define R_AARCH64_ABS64 257 /* Direct 64 bit. */
-#define R_AARCH64_ABS32 258 /* Direct 32 bit. */
-#define R_AARCH64_ABS16 259 /* Direct 16-bit. */
-#define R_AARCH64_PREL64 260 /* PC-relative 64-bit. */
-#define R_AARCH64_PREL32 261 /* PC-relative 32-bit. */
-#define R_AARCH64_PREL16 262 /* PC-relative 16-bit. */
-#define R_AARCH64_MOVW_UABS_G0 263 /* Dir. MOVZ imm. from bits 15:0. */
-#define R_AARCH64_MOVW_UABS_G0_NC 264 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_UABS_G1 265 /* Dir. MOVZ imm. from bits 31:16. */
-#define R_AARCH64_MOVW_UABS_G1_NC 266 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_UABS_G2 267 /* Dir. MOVZ imm. from bits 47:32. */
-#define R_AARCH64_MOVW_UABS_G2_NC 268 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_UABS_G3 269 /* Dir. MOV{K,Z} imm. from 63:48. */
-#define R_AARCH64_MOVW_SABS_G0 270 /* Dir. MOV{N,Z} imm. from 15:0. */
-#define R_AARCH64_MOVW_SABS_G1 271 /* Dir. MOV{N,Z} imm. from 31:16. */
-#define R_AARCH64_MOVW_SABS_G2 272 /* Dir. MOV{N,Z} imm. from 47:32. */
-#define R_AARCH64_LD_PREL_LO19 273 /* PC-rel. LD imm. from bits 20:2. */
-#define R_AARCH64_ADR_PREL_LO21 274 /* PC-rel. ADR imm. from bits 20:0. */
-#define R_AARCH64_ADR_PREL_PG_HI21 275 /* Page-rel. ADRP imm. from 32:12. */
-#define R_AARCH64_ADR_PREL_PG_HI21_NC 276 /* Likewise; no overflow check. */
-#define R_AARCH64_ADD_ABS_LO12_NC 277 /* Dir. ADD imm. from bits 11:0. */
-#define R_AARCH64_LDST8_ABS_LO12_NC 278 /* Likewise for LD/ST; no check. */
-#define R_AARCH64_TSTBR14 279 /* PC-rel. TBZ/TBNZ imm. from 15:2. */
-#define R_AARCH64_CONDBR19 280 /* PC-rel. cond. br. imm. from 20:2. */
-#define R_AARCH64_JUMP26 282 /* PC-rel. B imm. from bits 27:2. */
-#define R_AARCH64_CALL26 283 /* Likewise for CALL. */
-#define R_AARCH64_LDST16_ABS_LO12_NC 284 /* Dir. ADD imm. from bits 11:1. */
-#define R_AARCH64_LDST32_ABS_LO12_NC 285 /* Likewise for bits 11:2. */
-#define R_AARCH64_LDST64_ABS_LO12_NC 286 /* Likewise for bits 11:3. */
-#define R_AARCH64_MOVW_PREL_G0 287 /* PC-rel. MOV{N,Z} imm. from 15:0. */
-#define R_AARCH64_MOVW_PREL_G0_NC 288 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_PREL_G1 289 /* PC-rel. MOV{N,Z} imm. from 31:16. */
-#define R_AARCH64_MOVW_PREL_G1_NC 290 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_PREL_G2 291 /* PC-rel. MOV{N,Z} imm. from 47:32. */
-#define R_AARCH64_MOVW_PREL_G2_NC 292 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_PREL_G3 293 /* PC-rel. MOV{N,Z} imm. from 63:48. */
-#define R_AARCH64_LDST128_ABS_LO12_NC 299 /* Dir. ADD imm. from bits 11:4. */
-#define R_AARCH64_MOVW_GOTOFF_G0 300 /* GOT-rel. off. MOV{N,Z} imm. 15:0. */
-#define R_AARCH64_MOVW_GOTOFF_G0_NC 301 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_GOTOFF_G1 302 /* GOT-rel. o. MOV{N,Z} imm. 31:16. */
-#define R_AARCH64_MOVW_GOTOFF_G1_NC 303 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_GOTOFF_G2 304 /* GOT-rel. o. MOV{N,Z} imm. 47:32. */
-#define R_AARCH64_MOVW_GOTOFF_G2_NC 305 /* Likewise for MOVK; no check. */
-#define R_AARCH64_MOVW_GOTOFF_G3 306 /* GOT-rel. o. MOV{N,Z} imm. 63:48. */
-#define R_AARCH64_GOTREL64 307 /* GOT-relative 64-bit. */
-#define R_AARCH64_GOTREL32 308 /* GOT-relative 32-bit. */
-#define R_AARCH64_GOT_LD_PREL19 309 /* PC-rel. GOT off. load imm. 20:2. */
-#define R_AARCH64_LD64_GOTOFF_LO15 310 /* GOT-rel. off. LD/ST imm. 14:3. */
-#define R_AARCH64_ADR_GOT_PAGE 311 /* P-page-rel. GOT off. ADRP 32:12. */
-#define R_AARCH64_LD64_GOT_LO12_NC 312 /* Dir. GOT off. LD/ST imm. 11:3. */
-#define R_AARCH64_LD64_GOTPAGE_LO15 313 /* GOT-page-rel. GOT off. LD/ST 14:3 */
-#define R_AARCH64_TLSGD_ADR_PREL21 512 /* PC-relative ADR imm. 20:0. */
-#define R_AARCH64_TLSGD_ADR_PAGE21 513 /* page-rel. ADRP imm. 32:12. */
-#define R_AARCH64_TLSGD_ADD_LO12_NC 514 /* direct ADD imm. from 11:0. */
-#define R_AARCH64_TLSGD_MOVW_G1 515 /* GOT-rel. MOV{N,Z} 31:16. */
-#define R_AARCH64_TLSGD_MOVW_G0_NC 516 /* GOT-rel. MOVK imm. 15:0. */
-#define R_AARCH64_TLSLD_ADR_PREL21 517 /* Like 512; local dynamic model. */
-#define R_AARCH64_TLSLD_ADR_PAGE21 518 /* Like 513; local dynamic model. */
-#define R_AARCH64_TLSLD_ADD_LO12_NC 519 /* Like 514; local dynamic model. */
-#define R_AARCH64_TLSLD_MOVW_G1 520 /* Like 515; local dynamic model. */
-#define R_AARCH64_TLSLD_MOVW_G0_NC 521 /* Like 516; local dynamic model. */
-#define R_AARCH64_TLSLD_LD_PREL19 522 /* TLS PC-rel. load imm. 20:2. */
-#define R_AARCH64_TLSLD_MOVW_DTPREL_G2 523 /* TLS DTP-rel. MOV{N,Z} 47:32. */
-#define R_AARCH64_TLSLD_MOVW_DTPREL_G1 524 /* TLS DTP-rel. MOV{N,Z} 31:16. */
-#define R_AARCH64_TLSLD_MOVW_DTPREL_G1_NC 525 /* Likewise; MOVK; no check. */
-#define R_AARCH64_TLSLD_MOVW_DTPREL_G0 526 /* TLS DTP-rel. MOV{N,Z} 15:0. */
-#define R_AARCH64_TLSLD_MOVW_DTPREL_G0_NC 527 /* Likewise; MOVK; no check. */
-#define R_AARCH64_TLSLD_ADD_DTPREL_HI12 528 /* DTP-rel. ADD imm. from 23:12. */
-#define R_AARCH64_TLSLD_ADD_DTPREL_LO12 529 /* DTP-rel. ADD imm. from 11:0. */
-#define R_AARCH64_TLSLD_ADD_DTPREL_LO12_NC 530 /* Likewise; no ovfl. check. */
-#define R_AARCH64_TLSLD_LDST8_DTPREL_LO12 531 /* DTP-rel. LD/ST imm. 11:0. */
-#define R_AARCH64_TLSLD_LDST8_DTPREL_LO12_NC 532 /* Likewise; no check. */
-#define R_AARCH64_TLSLD_LDST16_DTPREL_LO12 533 /* DTP-rel. LD/ST imm. 11:1. */
-#define R_AARCH64_TLSLD_LDST16_DTPREL_LO12_NC 534 /* Likewise; no check. */
-#define R_AARCH64_TLSLD_LDST32_DTPREL_LO12 535 /* DTP-rel. LD/ST imm. 11:2. */
-#define R_AARCH64_TLSLD_LDST32_DTPREL_LO12_NC 536 /* Likewise; no check. */
-#define R_AARCH64_TLSLD_LDST64_DTPREL_LO12 537 /* DTP-rel. LD/ST imm. 11:3. */
-#define R_AARCH64_TLSLD_LDST64_DTPREL_LO12_NC 538 /* Likewise; no check. */
-#define R_AARCH64_TLSIE_MOVW_GOTTPREL_G1 539 /* GOT-rel. MOV{N,Z} 31:16. */
-#define R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC 540 /* GOT-rel. MOVK 15:0. */
-#define R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 541 /* Page-rel. ADRP 32:12. */
-#define R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC 542 /* Direct LD off. 11:3. */
-#define R_AARCH64_TLSIE_LD_GOTTPREL_PREL19 543 /* PC-rel. load imm. 20:2. */
-#define R_AARCH64_TLSLE_MOVW_TPREL_G2 544 /* TLS TP-rel. MOV{N,Z} 47:32. */
-#define R_AARCH64_TLSLE_MOVW_TPREL_G1 545 /* TLS TP-rel. MOV{N,Z} 31:16. */
-#define R_AARCH64_TLSLE_MOVW_TPREL_G1_NC 546 /* Likewise; MOVK; no check. */
-#define R_AARCH64_TLSLE_MOVW_TPREL_G0 547 /* TLS TP-rel. MOV{N,Z} 15:0. */
-#define R_AARCH64_TLSLE_MOVW_TPREL_G0_NC 548 /* Likewise; MOVK; no check. */
-#define R_AARCH64_TLSLE_ADD_TPREL_HI12 549 /* TP-rel. ADD imm. 23:12. */
-#define R_AARCH64_TLSLE_ADD_TPREL_LO12 550 /* TP-rel. ADD imm. 11:0. */
-#define R_AARCH64_TLSLE_ADD_TPREL_LO12_NC 551 /* Likewise; no ovfl. check. */
-#define R_AARCH64_TLSLE_LDST8_TPREL_LO12 552 /* TP-rel. LD/ST off. 11:0. */
-#define R_AARCH64_TLSLE_LDST8_TPREL_LO12_NC 553 /* Likewise; no ovfl. check. */
-#define R_AARCH64_TLSLE_LDST16_TPREL_LO12 554 /* TP-rel. LD/ST off. 11:1. */
-#define R_AARCH64_TLSLE_LDST16_TPREL_LO12_NC 555 /* Likewise; no check. */
-#define R_AARCH64_TLSLE_LDST32_TPREL_LO12 556 /* TP-rel. LD/ST off. 11:2. */
-#define R_AARCH64_TLSLE_LDST32_TPREL_LO12_NC 557 /* Likewise; no check. */
-#define R_AARCH64_TLSLE_LDST64_TPREL_LO12 558 /* TP-rel. LD/ST off. 11:3. */
-#define R_AARCH64_TLSLE_LDST64_TPREL_LO12_NC 559 /* Likewise; no check. */
-#define R_AARCH64_TLSDESC_LD_PREL19 560 /* PC-rel. load immediate 20:2. */
-#define R_AARCH64_TLSDESC_ADR_PREL21 561 /* PC-rel. ADR immediate 20:0. */
-#define R_AARCH64_TLSDESC_ADR_PAGE21 562 /* Page-rel. ADRP imm. 32:12. */
-#define R_AARCH64_TLSDESC_LD64_LO12 563 /* Direct LD off. from 11:3. */
-#define R_AARCH64_TLSDESC_ADD_LO12 564 /* Direct ADD imm. from 11:0. */
-#define R_AARCH64_TLSDESC_OFF_G1 565 /* GOT-rel. MOV{N,Z} imm. 31:16. */
-#define R_AARCH64_TLSDESC_OFF_G0_NC 566 /* GOT-rel. MOVK imm. 15:0; no ck. */
-#define R_AARCH64_TLSDESC_LDR 567 /* Relax LDR. */
-#define R_AARCH64_TLSDESC_ADD 568 /* Relax ADD. */
-#define R_AARCH64_TLSDESC_CALL 569 /* Relax BLR. */
-#define R_AARCH64_TLSLE_LDST128_TPREL_LO12 570 /* TP-rel. LD/ST off. 11:4. */
-#define R_AARCH64_TLSLE_LDST128_TPREL_LO12_NC 571 /* Likewise; no check. */
-#define R_AARCH64_TLSLD_LDST128_DTPREL_LO12 572 /* DTP-rel. LD/ST imm. 11:4. */
-#define R_AARCH64_TLSLD_LDST128_DTPREL_LO12_NC 573 /* Likewise; no check. */
-#define R_AARCH64_COPY 1024 /* Copy symbol at runtime. */
-#define R_AARCH64_GLOB_DAT 1025 /* Create GOT entry. */
-#define R_AARCH64_JUMP_SLOT 1026 /* Create PLT entry. */
-#define R_AARCH64_RELATIVE 1027 /* Adjust by program base. */
-#define R_AARCH64_TLS_DTPMOD 1028 /* Module number, 64 bit. */
-#define R_AARCH64_TLS_DTPREL 1029 /* Module-relative offset, 64 bit. */
-#define R_AARCH64_TLS_TPREL 1030 /* TP-relative offset, 64 bit. */
-#define R_AARCH64_TLSDESC 1031 /* TLS Descriptor. */
-#define R_AARCH64_IRELATIVE 1032 /* STT_GNU_IFUNC relocation. */
-
-/* ARM relocs. */
-
-#define R_ARM_NONE 0 /* No reloc */
-#define R_ARM_PC24 1 /* Deprecated PC relative 26
- bit branch. */
-#define R_ARM_ABS32 2 /* Direct 32 bit */
-#define R_ARM_REL32 3 /* PC relative 32 bit */
-#define R_ARM_PC13 4
-#define R_ARM_ABS16 5 /* Direct 16 bit */
-#define R_ARM_ABS12 6 /* Direct 12 bit */
-#define R_ARM_THM_ABS5 7 /* Direct & 0x7C (LDR, STR). */
-#define R_ARM_ABS8 8 /* Direct 8 bit */
-#define R_ARM_SBREL32 9
-#define R_ARM_THM_PC22 10 /* PC relative 24 bit (Thumb32 BL). */
-#define R_ARM_THM_PC8 11 /* PC relative & 0x3FC
- (Thumb16 LDR, ADD, ADR). */
-#define R_ARM_AMP_VCALL9 12
-#define R_ARM_SWI24 13 /* Obsolete static relocation. */
-#define R_ARM_TLS_DESC 13 /* Dynamic relocation. */
-#define R_ARM_THM_SWI8 14 /* Reserved. */
-#define R_ARM_XPC25 15 /* Reserved. */
-#define R_ARM_THM_XPC22 16 /* Reserved. */
-#define R_ARM_TLS_DTPMOD32 17 /* ID of module containing symbol */
-#define R_ARM_TLS_DTPOFF32 18 /* Offset in TLS block */
-#define R_ARM_TLS_TPOFF32 19 /* Offset in static TLS block */
-#define R_ARM_COPY 20 /* Copy symbol at runtime */
-#define R_ARM_GLOB_DAT 21 /* Create GOT entry */
-#define R_ARM_JUMP_SLOT 22 /* Create PLT entry */
-#define R_ARM_RELATIVE 23 /* Adjust by program base */
-#define R_ARM_GOTOFF 24 /* 32 bit offset to GOT */
-#define R_ARM_GOTPC 25 /* 32 bit PC relative offset to GOT */
-#define R_ARM_GOT32 26 /* 32 bit GOT entry */
-#define R_ARM_PLT32 27 /* Deprecated, 32 bit PLT address. */
-#define R_ARM_CALL 28 /* PC relative 24 bit (BL, BLX). */
-#define R_ARM_JUMP24 29 /* PC relative 24 bit
- (B, BL<cond>). */
-#define R_ARM_THM_JUMP24 30 /* PC relative 24 bit (Thumb32 B.W). */
-#define R_ARM_BASE_ABS 31 /* Adjust by program base. */
-#define R_ARM_ALU_PCREL_7_0 32 /* Obsolete. */
-#define R_ARM_ALU_PCREL_15_8 33 /* Obsolete. */
-#define R_ARM_ALU_PCREL_23_15 34 /* Obsolete. */
-#define R_ARM_LDR_SBREL_11_0 35 /* Deprecated, prog. base relative. */
-#define R_ARM_ALU_SBREL_19_12 36 /* Deprecated, prog. base relative. */
-#define R_ARM_ALU_SBREL_27_20 37 /* Deprecated, prog. base relative. */
-#define R_ARM_TARGET1 38
-#define R_ARM_SBREL31 39 /* Program base relative. */
-#define R_ARM_V4BX 40
-#define R_ARM_TARGET2 41
-#define R_ARM_PREL31 42 /* 32 bit PC relative. */
-#define R_ARM_MOVW_ABS_NC 43 /* Direct 16-bit (MOVW). */
-#define R_ARM_MOVT_ABS 44 /* Direct high 16-bit (MOVT). */
-#define R_ARM_MOVW_PREL_NC 45 /* PC relative 16-bit (MOVW). */
-#define R_ARM_MOVT_PREL 46 /* PC relative (MOVT). */
-#define R_ARM_THM_MOVW_ABS_NC 47 /* Direct 16 bit (Thumb32 MOVW). */
-#define R_ARM_THM_MOVT_ABS 48 /* Direct high 16 bit
- (Thumb32 MOVT). */
-#define R_ARM_THM_MOVW_PREL_NC 49 /* PC relative 16 bit
- (Thumb32 MOVW). */
-#define R_ARM_THM_MOVT_PREL 50 /* PC relative high 16 bit
- (Thumb32 MOVT). */
-#define R_ARM_THM_JUMP19 51 /* PC relative 20 bit
- (Thumb32 B<cond>.W). */
-#define R_ARM_THM_JUMP6 52 /* PC relative X & 0x7E
- (Thumb16 CBZ, CBNZ). */
-#define R_ARM_THM_ALU_PREL_11_0 53 /* PC relative 12 bit
- (Thumb32 ADR.W). */
-#define R_ARM_THM_PC12 54 /* PC relative 12 bit
- (Thumb32 LDR{D,SB,H,SH}). */
-#define R_ARM_ABS32_NOI 55 /* Direct 32-bit. */
-#define R_ARM_REL32_NOI 56 /* PC relative 32-bit. */
-#define R_ARM_ALU_PC_G0_NC 57 /* PC relative (ADD, SUB). */
-#define R_ARM_ALU_PC_G0 58 /* PC relative (ADD, SUB). */
-#define R_ARM_ALU_PC_G1_NC 59 /* PC relative (ADD, SUB). */
-#define R_ARM_ALU_PC_G1 60 /* PC relative (ADD, SUB). */
-#define R_ARM_ALU_PC_G2 61 /* PC relative (ADD, SUB). */
-#define R_ARM_LDR_PC_G1 62 /* PC relative (LDR,STR,LDRB,STRB). */
-#define R_ARM_LDR_PC_G2 63 /* PC relative (LDR,STR,LDRB,STRB). */
-#define R_ARM_LDRS_PC_G0 64 /* PC relative (STR{D,H},
- LDR{D,SB,H,SH}). */
-#define R_ARM_LDRS_PC_G1 65 /* PC relative (STR{D,H},
- LDR{D,SB,H,SH}). */
-#define R_ARM_LDRS_PC_G2 66 /* PC relative (STR{D,H},
- LDR{D,SB,H,SH}). */
-#define R_ARM_LDC_PC_G0 67 /* PC relative (LDC, STC). */
-#define R_ARM_LDC_PC_G1 68 /* PC relative (LDC, STC). */
-#define R_ARM_LDC_PC_G2 69 /* PC relative (LDC, STC). */
-#define R_ARM_ALU_SB_G0_NC 70 /* Program base relative (ADD,SUB). */
-#define R_ARM_ALU_SB_G0 71 /* Program base relative (ADD,SUB). */
-#define R_ARM_ALU_SB_G1_NC 72 /* Program base relative (ADD,SUB). */
-#define R_ARM_ALU_SB_G1 73 /* Program base relative (ADD,SUB). */
-#define R_ARM_ALU_SB_G2 74 /* Program base relative (ADD,SUB). */
-#define R_ARM_LDR_SB_G0 75 /* Program base relative (LDR,
- STR, LDRB, STRB). */
-#define R_ARM_LDR_SB_G1 76 /* Program base relative
- (LDR, STR, LDRB, STRB). */
-#define R_ARM_LDR_SB_G2 77 /* Program base relative
- (LDR, STR, LDRB, STRB). */
-#define R_ARM_LDRS_SB_G0 78 /* Program base relative
- (LDR, STR, LDRB, STRB). */
-#define R_ARM_LDRS_SB_G1 79 /* Program base relative
- (LDR, STR, LDRB, STRB). */
-#define R_ARM_LDRS_SB_G2 80 /* Program base relative
- (LDR, STR, LDRB, STRB). */
-#define R_ARM_LDC_SB_G0 81 /* Program base relative (LDC,STC). */
-#define R_ARM_LDC_SB_G1 82 /* Program base relative (LDC,STC). */
-#define R_ARM_LDC_SB_G2 83 /* Program base relative (LDC,STC). */
-#define R_ARM_MOVW_BREL_NC 84 /* Program base relative 16
- bit (MOVW). */
-#define R_ARM_MOVT_BREL 85 /* Program base relative high
- 16 bit (MOVT). */
-#define R_ARM_MOVW_BREL 86 /* Program base relative 16
- bit (MOVW). */
-#define R_ARM_THM_MOVW_BREL_NC 87 /* Program base relative 16
- bit (Thumb32 MOVW). */
-#define R_ARM_THM_MOVT_BREL 88 /* Program base relative high
- 16 bit (Thumb32 MOVT). */
-#define R_ARM_THM_MOVW_BREL 89 /* Program base relative 16
- bit (Thumb32 MOVW). */
-#define R_ARM_TLS_GOTDESC 90
-#define R_ARM_TLS_CALL 91
-#define R_ARM_TLS_DESCSEQ 92 /* TLS relaxation. */
-#define R_ARM_THM_TLS_CALL 93
-#define R_ARM_PLT32_ABS 94
-#define R_ARM_GOT_ABS 95 /* GOT entry. */
-#define R_ARM_GOT_PREL 96 /* PC relative GOT entry. */
-#define R_ARM_GOT_BREL12 97 /* GOT entry relative to GOT
- origin (LDR). */
-#define R_ARM_GOTOFF12 98 /* 12 bit, GOT entry relative
- to GOT origin (LDR, STR). */
-#define R_ARM_GOTRELAX 99
-#define R_ARM_GNU_VTENTRY 100
-#define R_ARM_GNU_VTINHERIT 101
-#define R_ARM_THM_PC11 102 /* PC relative & 0xFFE (Thumb16 B). */
-#define R_ARM_THM_PC9 103 /* PC relative & 0x1FE
- (Thumb16 B/B<cond>). */
-#define R_ARM_TLS_GD32 104 /* PC-rel 32 bit for global dynamic
- thread local data */
-#define R_ARM_TLS_LDM32 105 /* PC-rel 32 bit for local dynamic
- thread local data */
-#define R_ARM_TLS_LDO32 106 /* 32 bit offset relative to TLS
- block */
-#define R_ARM_TLS_IE32 107 /* PC-rel 32 bit for GOT entry of
- static TLS block offset */
-#define R_ARM_TLS_LE32 108 /* 32 bit offset relative to static
- TLS block */
-#define R_ARM_TLS_LDO12 109 /* 12 bit relative to TLS
- block (LDR, STR). */
-#define R_ARM_TLS_LE12 110 /* 12 bit relative to static
- TLS block (LDR, STR). */
-#define R_ARM_TLS_IE12GP 111 /* 12 bit GOT entry relative
- to GOT origin (LDR). */
-#define R_ARM_ME_TOO 128 /* Obsolete. */
-#define R_ARM_THM_TLS_DESCSEQ 129
-#define R_ARM_THM_TLS_DESCSEQ16 129
-#define R_ARM_THM_TLS_DESCSEQ32 130
-#define R_ARM_THM_GOT_BREL12 131 /* GOT entry relative to GOT
- origin, 12 bit (Thumb32 LDR). */
-#define R_ARM_IRELATIVE 160
-#define R_ARM_RXPC25 249
-#define R_ARM_RSBREL32 250
-#define R_ARM_THM_RPC22 251
-#define R_ARM_RREL32 252
-#define R_ARM_RABS22 253
-#define R_ARM_RPC24 254
-#define R_ARM_RBASE 255
-/* Keep this the last entry. */
-#define R_ARM_NUM 256
-
-/* IA-64 specific declarations. */
-
-/* Processor specific flags for the Ehdr e_flags field. */
-#define EF_IA_64_MASKOS 0x0000000f /* os-specific flags */
-#define EF_IA_64_ABI64 0x00000010 /* 64-bit ABI */
-#define EF_IA_64_ARCH 0xff000000 /* arch. version mask */
-
-/* Processor specific values for the Phdr p_type field. */
-#define PT_IA_64_ARCHEXT (PT_LOPROC + 0) /* arch extension bits */
-#define PT_IA_64_UNWIND (PT_LOPROC + 1) /* ia64 unwind bits */
-#define PT_IA_64_HP_OPT_ANOT (PT_LOOS + 0x12)
-#define PT_IA_64_HP_HSL_ANOT (PT_LOOS + 0x13)
-#define PT_IA_64_HP_STACK (PT_LOOS + 0x14)
-
-/* Processor specific flags for the Phdr p_flags field. */
-#define PF_IA_64_NORECOV 0x80000000 /* spec insns w/o recovery */
-
-/* Processor specific values for the Shdr sh_type field. */
-#define SHT_IA_64_EXT (SHT_LOPROC + 0) /* extension bits */
-#define SHT_IA_64_UNWIND (SHT_LOPROC + 1) /* unwind bits */
-
-/* Processor specific flags for the Shdr sh_flags field. */
-#define SHF_IA_64_SHORT 0x10000000 /* section near gp */
-#define SHF_IA_64_NORECOV 0x20000000 /* spec insns w/o recovery */
-
-/* Processor specific values for the Dyn d_tag field. */
-#define DT_IA_64_PLT_RESERVE (DT_LOPROC + 0)
-#define DT_IA_64_NUM 1
-
-/* IA-64 relocations. */
-#define R_IA64_NONE 0x00 /* none */
-#define R_IA64_IMM14 0x21 /* symbol + addend, add imm14 */
-#define R_IA64_IMM22 0x22 /* symbol + addend, add imm22 */
-#define R_IA64_IMM64 0x23 /* symbol + addend, mov imm64 */
-#define R_IA64_DIR32MSB 0x24 /* symbol + addend, data4 MSB */
-#define R_IA64_DIR32LSB 0x25 /* symbol + addend, data4 LSB */
-#define R_IA64_DIR64MSB 0x26 /* symbol + addend, data8 MSB */
-#define R_IA64_DIR64LSB 0x27 /* symbol + addend, data8 LSB */
-#define R_IA64_GPREL22 0x2a /* @gprel(sym + add), add imm22 */
-#define R_IA64_GPREL64I 0x2b /* @gprel(sym + add), mov imm64 */
-#define R_IA64_GPREL32MSB 0x2c /* @gprel(sym + add), data4 MSB */
-#define R_IA64_GPREL32LSB 0x2d /* @gprel(sym + add), data4 LSB */
-#define R_IA64_GPREL64MSB 0x2e /* @gprel(sym + add), data8 MSB */
-#define R_IA64_GPREL64LSB 0x2f /* @gprel(sym + add), data8 LSB */
-#define R_IA64_LTOFF22 0x32 /* @ltoff(sym + add), add imm22 */
-#define R_IA64_LTOFF64I 0x33 /* @ltoff(sym + add), mov imm64 */
-#define R_IA64_PLTOFF22 0x3a /* @pltoff(sym + add), add imm22 */
-#define R_IA64_PLTOFF64I 0x3b /* @pltoff(sym + add), mov imm64 */
-#define R_IA64_PLTOFF64MSB 0x3e /* @pltoff(sym + add), data8 MSB */
-#define R_IA64_PLTOFF64LSB 0x3f /* @pltoff(sym + add), data8 LSB */
-#define R_IA64_FPTR64I 0x43 /* @fptr(sym + add), mov imm64 */
-#define R_IA64_FPTR32MSB 0x44 /* @fptr(sym + add), data4 MSB */
-#define R_IA64_FPTR32LSB 0x45 /* @fptr(sym + add), data4 LSB */
-#define R_IA64_FPTR64MSB 0x46 /* @fptr(sym + add), data8 MSB */
-#define R_IA64_FPTR64LSB 0x47 /* @fptr(sym + add), data8 LSB */
-#define R_IA64_PCREL60B 0x48 /* @pcrel(sym + add), brl */
-#define R_IA64_PCREL21B 0x49 /* @pcrel(sym + add), ptb, call */
-#define R_IA64_PCREL21M 0x4a /* @pcrel(sym + add), chk.s */
-#define R_IA64_PCREL21F 0x4b /* @pcrel(sym + add), fchkf */
-#define R_IA64_PCREL32MSB 0x4c /* @pcrel(sym + add), data4 MSB */
-#define R_IA64_PCREL32LSB 0x4d /* @pcrel(sym + add), data4 LSB */
-#define R_IA64_PCREL64MSB 0x4e /* @pcrel(sym + add), data8 MSB */
-#define R_IA64_PCREL64LSB 0x4f /* @pcrel(sym + add), data8 LSB */
-#define R_IA64_LTOFF_FPTR22 0x52 /* @ltoff(@fptr(s+a)), imm22 */
-#define R_IA64_LTOFF_FPTR64I 0x53 /* @ltoff(@fptr(s+a)), imm64 */
-#define R_IA64_LTOFF_FPTR32MSB 0x54 /* @ltoff(@fptr(s+a)), data4 MSB */
-#define R_IA64_LTOFF_FPTR32LSB 0x55 /* @ltoff(@fptr(s+a)), data4 LSB */
-#define R_IA64_LTOFF_FPTR64MSB 0x56 /* @ltoff(@fptr(s+a)), data8 MSB */
-#define R_IA64_LTOFF_FPTR64LSB 0x57 /* @ltoff(@fptr(s+a)), data8 LSB */
-#define R_IA64_SEGREL32MSB 0x5c /* @segrel(sym + add), data4 MSB */
-#define R_IA64_SEGREL32LSB 0x5d /* @segrel(sym + add), data4 LSB */
-#define R_IA64_SEGREL64MSB 0x5e /* @segrel(sym + add), data8 MSB */
-#define R_IA64_SEGREL64LSB 0x5f /* @segrel(sym + add), data8 LSB */
-#define R_IA64_SECREL32MSB 0x64 /* @secrel(sym + add), data4 MSB */
-#define R_IA64_SECREL32LSB 0x65 /* @secrel(sym + add), data4 LSB */
-#define R_IA64_SECREL64MSB 0x66 /* @secrel(sym + add), data8 MSB */
-#define R_IA64_SECREL64LSB 0x67 /* @secrel(sym + add), data8 LSB */
-#define R_IA64_REL32MSB 0x6c /* data 4 + REL */
-#define R_IA64_REL32LSB 0x6d /* data 4 + REL */
-#define R_IA64_REL64MSB 0x6e /* data 8 + REL */
-#define R_IA64_REL64LSB 0x6f /* data 8 + REL */
-#define R_IA64_LTV32MSB 0x74 /* symbol + addend, data4 MSB */
-#define R_IA64_LTV32LSB 0x75 /* symbol + addend, data4 LSB */
-#define R_IA64_LTV64MSB 0x76 /* symbol + addend, data8 MSB */
-#define R_IA64_LTV64LSB 0x77 /* symbol + addend, data8 LSB */
-#define R_IA64_PCREL21BI 0x79 /* @pcrel(sym + add), 21bit inst */
-#define R_IA64_PCREL22 0x7a /* @pcrel(sym + add), 22bit inst */
-#define R_IA64_PCREL64I 0x7b /* @pcrel(sym + add), 64bit inst */
-#define R_IA64_IPLTMSB 0x80 /* dynamic reloc, imported PLT, MSB */
-#define R_IA64_IPLTLSB 0x81 /* dynamic reloc, imported PLT, LSB */
-#define R_IA64_COPY 0x84 /* copy relocation */
-#define R_IA64_SUB 0x85 /* Addend and symbol difference */
-#define R_IA64_LTOFF22X 0x86 /* LTOFF22, relaxable. */
-#define R_IA64_LDXMOV 0x87 /* Use of LTOFF22X. */
-#define R_IA64_TPREL14 0x91 /* @tprel(sym + add), imm14 */
-#define R_IA64_TPREL22 0x92 /* @tprel(sym + add), imm22 */
-#define R_IA64_TPREL64I 0x93 /* @tprel(sym + add), imm64 */
-#define R_IA64_TPREL64MSB 0x96 /* @tprel(sym + add), data8 MSB */
-#define R_IA64_TPREL64LSB 0x97 /* @tprel(sym + add), data8 LSB */
-#define R_IA64_LTOFF_TPREL22 0x9a /* @ltoff(@tprel(s+a)), imm2 */
-#define R_IA64_DTPMOD64MSB 0xa6 /* @dtpmod(sym + add), data8 MSB */
-#define R_IA64_DTPMOD64LSB 0xa7 /* @dtpmod(sym + add), data8 LSB */
-#define R_IA64_LTOFF_DTPMOD22 0xaa /* @ltoff(@dtpmod(sym + add)), imm22 */
-#define R_IA64_DTPREL14 0xb1 /* @dtprel(sym + add), imm14 */
-#define R_IA64_DTPREL22 0xb2 /* @dtprel(sym + add), imm22 */
-#define R_IA64_DTPREL64I 0xb3 /* @dtprel(sym + add), imm64 */
-#define R_IA64_DTPREL32MSB 0xb4 /* @dtprel(sym + add), data4 MSB */
-#define R_IA64_DTPREL32LSB 0xb5 /* @dtprel(sym + add), data4 LSB */
-#define R_IA64_DTPREL64MSB 0xb6 /* @dtprel(sym + add), data8 MSB */
-#define R_IA64_DTPREL64LSB 0xb7 /* @dtprel(sym + add), data8 LSB */
-#define R_IA64_LTOFF_DTPREL22 0xba /* @ltoff(@dtprel(s+a)), imm22 */
-
-/* SH specific declarations */
-
-/* Processor specific flags for the ELF header e_flags field. */
-#define EF_SH_MACH_MASK 0x1f
-#define EF_SH_UNKNOWN 0x0
-#define EF_SH1 0x1
-#define EF_SH2 0x2
-#define EF_SH3 0x3
-#define EF_SH_DSP 0x4
-#define EF_SH3_DSP 0x5
-#define EF_SH4AL_DSP 0x6
-#define EF_SH3E 0x8
-#define EF_SH4 0x9
-#define EF_SH2E 0xb
-#define EF_SH4A 0xc
-#define EF_SH2A 0xd
-#define EF_SH4_NOFPU 0x10
-#define EF_SH4A_NOFPU 0x11
-#define EF_SH4_NOMMU_NOFPU 0x12
-#define EF_SH2A_NOFPU 0x13
-#define EF_SH3_NOMMU 0x14
-#define EF_SH2A_SH4_NOFPU 0x15
-#define EF_SH2A_SH3_NOFPU 0x16
-#define EF_SH2A_SH4 0x17
-#define EF_SH2A_SH3E 0x18
-
-/* SH relocs. */
-#define R_SH_NONE 0
-#define R_SH_DIR32 1
-#define R_SH_REL32 2
-#define R_SH_DIR8WPN 3
-#define R_SH_IND12W 4
-#define R_SH_DIR8WPL 5
-#define R_SH_DIR8WPZ 6
-#define R_SH_DIR8BP 7
-#define R_SH_DIR8W 8
-#define R_SH_DIR8L 9
-#define R_SH_SWITCH16 25
-#define R_SH_SWITCH32 26
-#define R_SH_USES 27
-#define R_SH_COUNT 28
-#define R_SH_ALIGN 29
-#define R_SH_CODE 30
-#define R_SH_DATA 31
-#define R_SH_LABEL 32
-#define R_SH_SWITCH8 33
-#define R_SH_GNU_VTINHERIT 34
-#define R_SH_GNU_VTENTRY 35
-#define R_SH_TLS_GD_32 144
-#define R_SH_TLS_LD_32 145
-#define R_SH_TLS_LDO_32 146
-#define R_SH_TLS_IE_32 147
-#define R_SH_TLS_LE_32 148
-#define R_SH_TLS_DTPMOD32 149
-#define R_SH_TLS_DTPOFF32 150
-#define R_SH_TLS_TPOFF32 151
-#define R_SH_GOT32 160
-#define R_SH_PLT32 161
-#define R_SH_COPY 162
-#define R_SH_GLOB_DAT 163
-#define R_SH_JMP_SLOT 164
-#define R_SH_RELATIVE 165
-#define R_SH_GOTOFF 166
-#define R_SH_GOTPC 167
-/* Keep this the last entry. */
-#define R_SH_NUM 256
-
-/* S/390 specific definitions. */
-
-/* Valid values for the e_flags field. */
-
-#define EF_S390_HIGH_GPRS 0x00000001 /* High GPRs kernel facility needed. */
-
-/* Additional s390 relocs */
-
-#define R_390_NONE 0 /* No reloc. */
-#define R_390_8 1 /* Direct 8 bit. */
-#define R_390_12 2 /* Direct 12 bit. */
-#define R_390_16 3 /* Direct 16 bit. */
-#define R_390_32 4 /* Direct 32 bit. */
-#define R_390_PC32 5 /* PC relative 32 bit. */
-#define R_390_GOT12 6 /* 12 bit GOT offset. */
-#define R_390_GOT32 7 /* 32 bit GOT offset. */
-#define R_390_PLT32 8 /* 32 bit PC relative PLT address. */
-#define R_390_COPY 9 /* Copy symbol at runtime. */
-#define R_390_GLOB_DAT 10 /* Create GOT entry. */
-#define R_390_JMP_SLOT 11 /* Create PLT entry. */
-#define R_390_RELATIVE 12 /* Adjust by program base. */
-#define R_390_GOTOFF32 13 /* 32 bit offset to GOT. */
-#define R_390_GOTPC 14 /* 32 bit PC relative offset to GOT. */
-#define R_390_GOT16 15 /* 16 bit GOT offset. */
-#define R_390_PC16 16 /* PC relative 16 bit. */
-#define R_390_PC16DBL 17 /* PC relative 16 bit shifted by 1. */
-#define R_390_PLT16DBL 18 /* 16 bit PC rel. PLT shifted by 1. */
-#define R_390_PC32DBL 19 /* PC relative 32 bit shifted by 1. */
-#define R_390_PLT32DBL 20 /* 32 bit PC rel. PLT shifted by 1. */
-#define R_390_GOTPCDBL 21 /* 32 bit PC rel. GOT shifted by 1. */
-#define R_390_64 22 /* Direct 64 bit. */
-#define R_390_PC64 23 /* PC relative 64 bit. */
-#define R_390_GOT64 24 /* 64 bit GOT offset. */
-#define R_390_PLT64 25 /* 64 bit PC relative PLT address. */
-#define R_390_GOTENT 26 /* 32 bit PC rel. to GOT entry >> 1. */
-#define R_390_GOTOFF16 27 /* 16 bit offset to GOT. */
-#define R_390_GOTOFF64 28 /* 64 bit offset to GOT. */
-#define R_390_GOTPLT12 29 /* 12 bit offset to jump slot. */
-#define R_390_GOTPLT16 30 /* 16 bit offset to jump slot. */
-#define R_390_GOTPLT32 31 /* 32 bit offset to jump slot. */
-#define R_390_GOTPLT64 32 /* 64 bit offset to jump slot. */
-#define R_390_GOTPLTENT 33 /* 32 bit rel. offset to jump slot. */
-#define R_390_PLTOFF16 34 /* 16 bit offset from GOT to PLT. */
-#define R_390_PLTOFF32 35 /* 32 bit offset from GOT to PLT. */
-#define R_390_PLTOFF64 36 /* 16 bit offset from GOT to PLT. */
-#define R_390_TLS_LOAD 37 /* Tag for load insn in TLS code. */
-#define R_390_TLS_GDCALL 38 /* Tag for function call in general
- dynamic TLS code. */
-#define R_390_TLS_LDCALL 39 /* Tag for function call in local
- dynamic TLS code. */
-#define R_390_TLS_GD32 40 /* Direct 32 bit for general dynamic
- thread local data. */
-#define R_390_TLS_GD64 41 /* Direct 64 bit for general dynamic
- thread local data. */
-#define R_390_TLS_GOTIE12 42 /* 12 bit GOT offset for static TLS
- block offset. */
-#define R_390_TLS_GOTIE32 43 /* 32 bit GOT offset for static TLS
- block offset. */
-#define R_390_TLS_GOTIE64 44 /* 64 bit GOT offset for static TLS
- block offset. */
-#define R_390_TLS_LDM32 45 /* Direct 32 bit for local dynamic
- thread local data in LE code. */
-#define R_390_TLS_LDM64 46 /* Direct 64 bit for local dynamic
- thread local data in LE code. */
-#define R_390_TLS_IE32 47 /* 32 bit address of GOT entry for
- negated static TLS block offset. */
-#define R_390_TLS_IE64 48 /* 64 bit address of GOT entry for
- negated static TLS block offset. */
-#define R_390_TLS_IEENT 49 /* 32 bit rel. offset to GOT entry for
- negated static TLS block offset. */
-#define R_390_TLS_LE32 50 /* 32 bit negated offset relative to
- static TLS block. */
-#define R_390_TLS_LE64 51 /* 64 bit negated offset relative to
- static TLS block. */
-#define R_390_TLS_LDO32 52 /* 32 bit offset relative to TLS
- block. */
-#define R_390_TLS_LDO64 53 /* 64 bit offset relative to TLS
- block. */
-#define R_390_TLS_DTPMOD 54 /* ID of module containing symbol. */
-#define R_390_TLS_DTPOFF 55 /* Offset in TLS block. */
-#define R_390_TLS_TPOFF 56 /* Negated offset in static TLS
- block. */
-#define R_390_20 57 /* Direct 20 bit. */
-#define R_390_GOT20 58 /* 20 bit GOT offset. */
-#define R_390_GOTPLT20 59 /* 20 bit offset to jump slot. */
-#define R_390_TLS_GOTIE20 60 /* 20 bit GOT offset for static TLS
- block offset. */
-#define R_390_IRELATIVE 61 /* STT_GNU_IFUNC relocation. */
-/* Keep this the last entry. */
-#define R_390_NUM 62
-
-
-/* CRIS relocations. */
-#define R_CRIS_NONE 0
-#define R_CRIS_8 1
-#define R_CRIS_16 2
-#define R_CRIS_32 3
-#define R_CRIS_8_PCREL 4
-#define R_CRIS_16_PCREL 5
-#define R_CRIS_32_PCREL 6
-#define R_CRIS_GNU_VTINHERIT 7
-#define R_CRIS_GNU_VTENTRY 8
-#define R_CRIS_COPY 9
-#define R_CRIS_GLOB_DAT 10
-#define R_CRIS_JUMP_SLOT 11
-#define R_CRIS_RELATIVE 12
-#define R_CRIS_16_GOT 13
-#define R_CRIS_32_GOT 14
-#define R_CRIS_16_GOTPLT 15
-#define R_CRIS_32_GOTPLT 16
-#define R_CRIS_32_GOTREL 17
-#define R_CRIS_32_PLT_GOTREL 18
-#define R_CRIS_32_PLT_PCREL 19
-
-#define R_CRIS_NUM 20
-
-
-/* AMD x86-64 relocations. */
-#define R_X86_64_NONE 0 /* No reloc */
-#define R_X86_64_64 1 /* Direct 64 bit */
-#define R_X86_64_PC32 2 /* PC relative 32 bit signed */
-#define R_X86_64_GOT32 3 /* 32 bit GOT entry */
-#define R_X86_64_PLT32 4 /* 32 bit PLT address */
-#define R_X86_64_COPY 5 /* Copy symbol at runtime */
-#define R_X86_64_GLOB_DAT 6 /* Create GOT entry */
-#define R_X86_64_JUMP_SLOT 7 /* Create PLT entry */
-#define R_X86_64_RELATIVE 8 /* Adjust by program base */
-#define R_X86_64_GOTPCREL 9 /* 32 bit signed PC relative
- offset to GOT */
-#define R_X86_64_32 10 /* Direct 32 bit zero extended */
-#define R_X86_64_32S 11 /* Direct 32 bit sign extended */
-#define R_X86_64_16 12 /* Direct 16 bit zero extended */
-#define R_X86_64_PC16 13 /* 16 bit sign extended pc relative */
-#define R_X86_64_8 14 /* Direct 8 bit sign extended */
-#define R_X86_64_PC8 15 /* 8 bit sign extended pc relative */
-#define R_X86_64_DTPMOD64 16 /* ID of module containing symbol */
-#define R_X86_64_DTPOFF64 17 /* Offset in module's TLS block */
-#define R_X86_64_TPOFF64 18 /* Offset in initial TLS block */
-#define R_X86_64_TLSGD 19 /* 32 bit signed PC relative offset
- to two GOT entries for GD symbol */
-#define R_X86_64_TLSLD 20 /* 32 bit signed PC relative offset
- to two GOT entries for LD symbol */
-#define R_X86_64_DTPOFF32 21 /* Offset in TLS block */
-#define R_X86_64_GOTTPOFF 22 /* 32 bit signed PC relative offset
- to GOT entry for IE symbol */
-#define R_X86_64_TPOFF32 23 /* Offset in initial TLS block */
-#define R_X86_64_PC64 24 /* PC relative 64 bit */
-#define R_X86_64_GOTOFF64 25 /* 64 bit offset to GOT */
-#define R_X86_64_GOTPC32 26 /* 32 bit signed pc relative
- offset to GOT */
-#define R_X86_64_GOT64 27 /* 64-bit GOT entry offset */
-#define R_X86_64_GOTPCREL64 28 /* 64-bit PC relative offset
- to GOT entry */
-#define R_X86_64_GOTPC64 29 /* 64-bit PC relative offset to GOT */
-#define R_X86_64_GOTPLT64 30 /* like GOT64, says PLT entry needed */
-#define R_X86_64_PLTOFF64 31 /* 64-bit GOT relative offset
- to PLT entry */
-#define R_X86_64_SIZE32 32 /* Size of symbol plus 32-bit addend */
-#define R_X86_64_SIZE64 33 /* Size of symbol plus 64-bit addend */
-#define R_X86_64_GOTPC32_TLSDESC 34 /* GOT offset for TLS descriptor. */
-#define R_X86_64_TLSDESC_CALL 35 /* Marker for call through TLS
- descriptor. */
-#define R_X86_64_TLSDESC 36 /* TLS descriptor. */
-#define R_X86_64_IRELATIVE 37 /* Adjust indirectly by program base */
-#define R_X86_64_RELATIVE64 38 /* 64-bit adjust by program base */
- /* 39 Reserved was R_X86_64_PC32_BND */
- /* 40 Reserved was R_X86_64_PLT32_BND */
-#define R_X86_64_GOTPCRELX 41 /* Load from 32 bit signed pc relative
- offset to GOT entry without REX
- prefix, relaxable. */
-#define R_X86_64_REX_GOTPCRELX 42 /* Load from 32 bit signed pc relative
- offset to GOT entry with REX prefix,
- relaxable. */
-#define R_X86_64_NUM 43
-
-
-/* AM33 relocations. */
-#define R_MN10300_NONE 0 /* No reloc. */
-#define R_MN10300_32 1 /* Direct 32 bit. */
-#define R_MN10300_16 2 /* Direct 16 bit. */
-#define R_MN10300_8 3 /* Direct 8 bit. */
-#define R_MN10300_PCREL32 4 /* PC-relative 32-bit. */
-#define R_MN10300_PCREL16 5 /* PC-relative 16-bit signed. */
-#define R_MN10300_PCREL8 6 /* PC-relative 8-bit signed. */
-#define R_MN10300_GNU_VTINHERIT 7 /* Ancient C++ vtable garbage... */
-#define R_MN10300_GNU_VTENTRY 8 /* ... collection annotation. */
-#define R_MN10300_24 9 /* Direct 24 bit. */
-#define R_MN10300_GOTPC32 10 /* 32-bit PCrel offset to GOT. */
-#define R_MN10300_GOTPC16 11 /* 16-bit PCrel offset to GOT. */
-#define R_MN10300_GOTOFF32 12 /* 32-bit offset from GOT. */
-#define R_MN10300_GOTOFF24 13 /* 24-bit offset from GOT. */
-#define R_MN10300_GOTOFF16 14 /* 16-bit offset from GOT. */
-#define R_MN10300_PLT32 15 /* 32-bit PCrel to PLT entry. */
-#define R_MN10300_PLT16 16 /* 16-bit PCrel to PLT entry. */
-#define R_MN10300_GOT32 17 /* 32-bit offset to GOT entry. */
-#define R_MN10300_GOT24 18 /* 24-bit offset to GOT entry. */
-#define R_MN10300_GOT16 19 /* 16-bit offset to GOT entry. */
-#define R_MN10300_COPY 20 /* Copy symbol at runtime. */
-#define R_MN10300_GLOB_DAT 21 /* Create GOT entry. */
-#define R_MN10300_JMP_SLOT 22 /* Create PLT entry. */
-#define R_MN10300_RELATIVE 23 /* Adjust by program base. */
-#define R_MN10300_TLS_GD 24 /* 32-bit offset for global dynamic. */
-#define R_MN10300_TLS_LD 25 /* 32-bit offset for local dynamic. */
-#define R_MN10300_TLS_LDO 26 /* Module-relative offset. */
-#define R_MN10300_TLS_GOTIE 27 /* GOT offset for static TLS block
- offset. */
-#define R_MN10300_TLS_IE 28 /* GOT address for static TLS block
- offset. */
-#define R_MN10300_TLS_LE 29 /* Offset relative to static TLS
- block. */
-#define R_MN10300_TLS_DTPMOD 30 /* ID of module containing symbol. */
-#define R_MN10300_TLS_DTPOFF 31 /* Offset in module TLS block. */
-#define R_MN10300_TLS_TPOFF 32 /* Offset in static TLS block. */
-#define R_MN10300_SYM_DIFF 33 /* Adjustment for next reloc as needed
- by linker relaxation. */
-#define R_MN10300_ALIGN 34 /* Alignment requirement for linker
- relaxation. */
-#define R_MN10300_NUM 35
-
-
-/* M32R relocs. */
-#define R_M32R_NONE 0 /* No reloc. */
-#define R_M32R_16 1 /* Direct 16 bit. */
-#define R_M32R_32 2 /* Direct 32 bit. */
-#define R_M32R_24 3 /* Direct 24 bit. */
-#define R_M32R_10_PCREL 4 /* PC relative 10 bit shifted. */
-#define R_M32R_18_PCREL 5 /* PC relative 18 bit shifted. */
-#define R_M32R_26_PCREL 6 /* PC relative 26 bit shifted. */
-#define R_M32R_HI16_ULO 7 /* High 16 bit with unsigned low. */
-#define R_M32R_HI16_SLO 8 /* High 16 bit with signed low. */
-#define R_M32R_LO16 9 /* Low 16 bit. */
-#define R_M32R_SDA16 10 /* 16 bit offset in SDA. */
-#define R_M32R_GNU_VTINHERIT 11
-#define R_M32R_GNU_VTENTRY 12
-/* M32R relocs use SHT_RELA. */
-#define R_M32R_16_RELA 33 /* Direct 16 bit. */
-#define R_M32R_32_RELA 34 /* Direct 32 bit. */
-#define R_M32R_24_RELA 35 /* Direct 24 bit. */
-#define R_M32R_10_PCREL_RELA 36 /* PC relative 10 bit shifted. */
-#define R_M32R_18_PCREL_RELA 37 /* PC relative 18 bit shifted. */
-#define R_M32R_26_PCREL_RELA 38 /* PC relative 26 bit shifted. */
-#define R_M32R_HI16_ULO_RELA 39 /* High 16 bit with unsigned low */
-#define R_M32R_HI16_SLO_RELA 40 /* High 16 bit with signed low */
-#define R_M32R_LO16_RELA 41 /* Low 16 bit */
-#define R_M32R_SDA16_RELA 42 /* 16 bit offset in SDA */
-#define R_M32R_RELA_GNU_VTINHERIT 43
-#define R_M32R_RELA_GNU_VTENTRY 44
-#define R_M32R_REL32 45 /* PC relative 32 bit. */
-
-#define R_M32R_GOT24 48 /* 24 bit GOT entry */
-#define R_M32R_26_PLTREL 49 /* 26 bit PC relative to PLT shifted */
-#define R_M32R_COPY 50 /* Copy symbol at runtime */
-#define R_M32R_GLOB_DAT 51 /* Create GOT entry */
-#define R_M32R_JMP_SLOT 52 /* Create PLT entry */
-#define R_M32R_RELATIVE 53 /* Adjust by program base */
-#define R_M32R_GOTOFF 54 /* 24 bit offset to GOT */
-#define R_M32R_GOTPC24 55 /* 24 bit PC relative offset to GOT */
-#define R_M32R_GOT16_HI_ULO 56 /* High 16 bit GOT entry with unsigned
- low */
-#define R_M32R_GOT16_HI_SLO 57 /* High 16 bit GOT entry with signed
- low */
-#define R_M32R_GOT16_LO 58 /* Low 16 bit GOT entry */
-#define R_M32R_GOTPC_HI_ULO 59 /* High 16 bit PC relative offset to
- GOT with unsigned low */
-#define R_M32R_GOTPC_HI_SLO 60 /* High 16 bit PC relative offset to
- GOT with signed low */
-#define R_M32R_GOTPC_LO 61 /* Low 16 bit PC relative offset to
- GOT */
-#define R_M32R_GOTOFF_HI_ULO 62 /* High 16 bit offset to GOT
- with unsigned low */
-#define R_M32R_GOTOFF_HI_SLO 63 /* High 16 bit offset to GOT
- with signed low */
-#define R_M32R_GOTOFF_LO 64 /* Low 16 bit offset to GOT */
-#define R_M32R_NUM 256 /* Keep this the last entry. */
-
-/* MicroBlaze relocations */
-#define R_MICROBLAZE_NONE 0 /* No reloc. */
-#define R_MICROBLAZE_32 1 /* Direct 32 bit. */
-#define R_MICROBLAZE_32_PCREL 2 /* PC relative 32 bit. */
-#define R_MICROBLAZE_64_PCREL 3 /* PC relative 64 bit. */
-#define R_MICROBLAZE_32_PCREL_LO 4 /* Low 16 bits of PCREL32. */
-#define R_MICROBLAZE_64 5 /* Direct 64 bit. */
-#define R_MICROBLAZE_32_LO 6 /* Low 16 bit. */
-#define R_MICROBLAZE_SRO32 7 /* Read-only small data area. */
-#define R_MICROBLAZE_SRW32 8 /* Read-write small data area. */
-#define R_MICROBLAZE_64_NONE 9 /* No reloc. */
-#define R_MICROBLAZE_32_SYM_OP_SYM 10 /* Symbol Op Symbol relocation. */
-#define R_MICROBLAZE_GNU_VTINHERIT 11 /* GNU C++ vtable hierarchy. */
-#define R_MICROBLAZE_GNU_VTENTRY 12 /* GNU C++ vtable member usage. */
-#define R_MICROBLAZE_GOTPC_64 13 /* PC-relative GOT offset. */
-#define R_MICROBLAZE_GOT_64 14 /* GOT entry offset. */
-#define R_MICROBLAZE_PLT_64 15 /* PLT offset (PC-relative). */
-#define R_MICROBLAZE_REL 16 /* Adjust by program base. */
-#define R_MICROBLAZE_JUMP_SLOT 17 /* Create PLT entry. */
-#define R_MICROBLAZE_GLOB_DAT 18 /* Create GOT entry. */
-#define R_MICROBLAZE_GOTOFF_64 19 /* 64 bit offset to GOT. */
-#define R_MICROBLAZE_GOTOFF_32 20 /* 32 bit offset to GOT. */
-#define R_MICROBLAZE_COPY 21 /* Runtime copy. */
-#define R_MICROBLAZE_TLS 22 /* TLS Reloc. */
-#define R_MICROBLAZE_TLSGD 23 /* TLS General Dynamic. */
-#define R_MICROBLAZE_TLSLD 24 /* TLS Local Dynamic. */
-#define R_MICROBLAZE_TLSDTPMOD32 25 /* TLS Module ID. */
-#define R_MICROBLAZE_TLSDTPREL32 26 /* TLS Offset Within TLS Block. */
-#define R_MICROBLAZE_TLSDTPREL64 27 /* TLS Offset Within TLS Block. */
-#define R_MICROBLAZE_TLSGOTTPREL32 28 /* TLS Offset From Thread Pointer. */
-#define R_MICROBLAZE_TLSTPREL32 29 /* TLS Offset From Thread Pointer. */
-
-/* Legal values for d_tag (dynamic entry type). */
-#define DT_NIOS2_GP 0x70000002 /* Address of _gp. */
-
-/* Nios II relocations. */
-#define R_NIOS2_NONE 0 /* No reloc. */
-#define R_NIOS2_S16 1 /* Direct signed 16 bit. */
-#define R_NIOS2_U16 2 /* Direct unsigned 16 bit. */
-#define R_NIOS2_PCREL16 3 /* PC relative 16 bit. */
-#define R_NIOS2_CALL26 4 /* Direct call. */
-#define R_NIOS2_IMM5 5 /* 5 bit constant expression. */
-#define R_NIOS2_CACHE_OPX 6 /* 5 bit expression, shift 22. */
-#define R_NIOS2_IMM6 7 /* 6 bit constant expression. */
-#define R_NIOS2_IMM8 8 /* 8 bit constant expression. */
-#define R_NIOS2_HI16 9 /* High 16 bit. */
-#define R_NIOS2_LO16 10 /* Low 16 bit. */
-#define R_NIOS2_HIADJ16 11 /* High 16 bit, adjusted. */
-#define R_NIOS2_BFD_RELOC_32 12 /* 32 bit symbol value + addend. */
-#define R_NIOS2_BFD_RELOC_16 13 /* 16 bit symbol value + addend. */
-#define R_NIOS2_BFD_RELOC_8 14 /* 8 bit symbol value + addend. */
-#define R_NIOS2_GPREL 15 /* 16 bit GP pointer offset. */
-#define R_NIOS2_GNU_VTINHERIT 16 /* GNU C++ vtable hierarchy. */
-#define R_NIOS2_GNU_VTENTRY 17 /* GNU C++ vtable member usage. */
-#define R_NIOS2_UJMP 18 /* Unconditional branch. */
-#define R_NIOS2_CJMP 19 /* Conditional branch. */
-#define R_NIOS2_CALLR 20 /* Indirect call through register. */
-#define R_NIOS2_ALIGN 21 /* Alignment requirement for
- linker relaxation. */
-#define R_NIOS2_GOT16 22 /* 16 bit GOT entry. */
-#define R_NIOS2_CALL16 23 /* 16 bit GOT entry for function. */
-#define R_NIOS2_GOTOFF_LO 24 /* %lo of offset to GOT pointer. */
-#define R_NIOS2_GOTOFF_HA 25 /* %hiadj of offset to GOT pointer. */
-#define R_NIOS2_PCREL_LO 26 /* %lo of PC relative offset. */
-#define R_NIOS2_PCREL_HA 27 /* %hiadj of PC relative offset. */
-#define R_NIOS2_TLS_GD16 28 /* 16 bit GOT offset for TLS GD. */
-#define R_NIOS2_TLS_LDM16 29 /* 16 bit GOT offset for TLS LDM. */
-#define R_NIOS2_TLS_LDO16 30 /* 16 bit module relative offset. */
-#define R_NIOS2_TLS_IE16 31 /* 16 bit GOT offset for TLS IE. */
-#define R_NIOS2_TLS_LE16 32 /* 16 bit LE TP-relative offset. */
-#define R_NIOS2_TLS_DTPMOD 33 /* Module number. */
-#define R_NIOS2_TLS_DTPREL 34 /* Module-relative offset. */
-#define R_NIOS2_TLS_TPREL 35 /* TP-relative offset. */
-#define R_NIOS2_COPY 36 /* Copy symbol at runtime. */
-#define R_NIOS2_GLOB_DAT 37 /* Create GOT entry. */
-#define R_NIOS2_JUMP_SLOT 38 /* Create PLT entry. */
-#define R_NIOS2_RELATIVE 39 /* Adjust by program base. */
-#define R_NIOS2_GOTOFF 40 /* 16 bit offset to GOT pointer. */
-#define R_NIOS2_CALL26_NOAT 41 /* Direct call in .noat section. */
-#define R_NIOS2_GOT_LO 42 /* %lo() of GOT entry. */
-#define R_NIOS2_GOT_HA 43 /* %hiadj() of GOT entry. */
-#define R_NIOS2_CALL_LO 44 /* %lo() of function GOT entry. */
-#define R_NIOS2_CALL_HA 45 /* %hiadj() of function GOT entry. */
-
-/* TILEPro relocations. */
-#define R_TILEPRO_NONE 0 /* No reloc */
-#define R_TILEPRO_32 1 /* Direct 32 bit */
-#define R_TILEPRO_16 2 /* Direct 16 bit */
-#define R_TILEPRO_8 3 /* Direct 8 bit */
-#define R_TILEPRO_32_PCREL 4 /* PC relative 32 bit */
-#define R_TILEPRO_16_PCREL 5 /* PC relative 16 bit */
-#define R_TILEPRO_8_PCREL 6 /* PC relative 8 bit */
-#define R_TILEPRO_LO16 7 /* Low 16 bit */
-#define R_TILEPRO_HI16 8 /* High 16 bit */
-#define R_TILEPRO_HA16 9 /* High 16 bit, adjusted */
-#define R_TILEPRO_COPY 10 /* Copy relocation */
-#define R_TILEPRO_GLOB_DAT 11 /* Create GOT entry */
-#define R_TILEPRO_JMP_SLOT 12 /* Create PLT entry */
-#define R_TILEPRO_RELATIVE 13 /* Adjust by program base */
-#define R_TILEPRO_BROFF_X1 14 /* X1 pipe branch offset */
-#define R_TILEPRO_JOFFLONG_X1 15 /* X1 pipe jump offset */
-#define R_TILEPRO_JOFFLONG_X1_PLT 16 /* X1 pipe jump offset to PLT */
-#define R_TILEPRO_IMM8_X0 17 /* X0 pipe 8-bit */
-#define R_TILEPRO_IMM8_Y0 18 /* Y0 pipe 8-bit */
-#define R_TILEPRO_IMM8_X1 19 /* X1 pipe 8-bit */
-#define R_TILEPRO_IMM8_Y1 20 /* Y1 pipe 8-bit */
-#define R_TILEPRO_MT_IMM15_X1 21 /* X1 pipe mtspr */
-#define R_TILEPRO_MF_IMM15_X1 22 /* X1 pipe mfspr */
-#define R_TILEPRO_IMM16_X0 23 /* X0 pipe 16-bit */
-#define R_TILEPRO_IMM16_X1 24 /* X1 pipe 16-bit */
-#define R_TILEPRO_IMM16_X0_LO 25 /* X0 pipe low 16-bit */
-#define R_TILEPRO_IMM16_X1_LO 26 /* X1 pipe low 16-bit */
-#define R_TILEPRO_IMM16_X0_HI 27 /* X0 pipe high 16-bit */
-#define R_TILEPRO_IMM16_X1_HI 28 /* X1 pipe high 16-bit */
-#define R_TILEPRO_IMM16_X0_HA 29 /* X0 pipe high 16-bit, adjusted */
-#define R_TILEPRO_IMM16_X1_HA 30 /* X1 pipe high 16-bit, adjusted */
-#define R_TILEPRO_IMM16_X0_PCREL 31 /* X0 pipe PC relative 16 bit */
-#define R_TILEPRO_IMM16_X1_PCREL 32 /* X1 pipe PC relative 16 bit */
-#define R_TILEPRO_IMM16_X0_LO_PCREL 33 /* X0 pipe PC relative low 16 bit */
-#define R_TILEPRO_IMM16_X1_LO_PCREL 34 /* X1 pipe PC relative low 16 bit */
-#define R_TILEPRO_IMM16_X0_HI_PCREL 35 /* X0 pipe PC relative high 16 bit */
-#define R_TILEPRO_IMM16_X1_HI_PCREL 36 /* X1 pipe PC relative high 16 bit */
-#define R_TILEPRO_IMM16_X0_HA_PCREL 37 /* X0 pipe PC relative ha() 16 bit */
-#define R_TILEPRO_IMM16_X1_HA_PCREL 38 /* X1 pipe PC relative ha() 16 bit */
-#define R_TILEPRO_IMM16_X0_GOT 39 /* X0 pipe 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X1_GOT 40 /* X1 pipe 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X0_GOT_LO 41 /* X0 pipe low 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X1_GOT_LO 42 /* X1 pipe low 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X0_GOT_HI 43 /* X0 pipe high 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X1_GOT_HI 44 /* X1 pipe high 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X0_GOT_HA 45 /* X0 pipe ha() 16-bit GOT offset */
-#define R_TILEPRO_IMM16_X1_GOT_HA 46 /* X1 pipe ha() 16-bit GOT offset */
-#define R_TILEPRO_MMSTART_X0 47 /* X0 pipe mm "start" */
-#define R_TILEPRO_MMEND_X0 48 /* X0 pipe mm "end" */
-#define R_TILEPRO_MMSTART_X1 49 /* X1 pipe mm "start" */
-#define R_TILEPRO_MMEND_X1 50 /* X1 pipe mm "end" */
-#define R_TILEPRO_SHAMT_X0 51 /* X0 pipe shift amount */
-#define R_TILEPRO_SHAMT_X1 52 /* X1 pipe shift amount */
-#define R_TILEPRO_SHAMT_Y0 53 /* Y0 pipe shift amount */
-#define R_TILEPRO_SHAMT_Y1 54 /* Y1 pipe shift amount */
-#define R_TILEPRO_DEST_IMM8_X1 55 /* X1 pipe destination 8-bit */
-/* Relocs 56-59 are currently not defined. */
-#define R_TILEPRO_TLS_GD_CALL 60 /* "jal" for TLS GD */
-#define R_TILEPRO_IMM8_X0_TLS_GD_ADD 61 /* X0 pipe "addi" for TLS GD */
-#define R_TILEPRO_IMM8_X1_TLS_GD_ADD 62 /* X1 pipe "addi" for TLS GD */
-#define R_TILEPRO_IMM8_Y0_TLS_GD_ADD 63 /* Y0 pipe "addi" for TLS GD */
-#define R_TILEPRO_IMM8_Y1_TLS_GD_ADD 64 /* Y1 pipe "addi" for TLS GD */
-#define R_TILEPRO_TLS_IE_LOAD 65 /* "lw_tls" for TLS IE */
-#define R_TILEPRO_IMM16_X0_TLS_GD 66 /* X0 pipe 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X1_TLS_GD 67 /* X1 pipe 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X0_TLS_GD_LO 68 /* X0 pipe low 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X1_TLS_GD_LO 69 /* X1 pipe low 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X0_TLS_GD_HI 70 /* X0 pipe high 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X1_TLS_GD_HI 71 /* X1 pipe high 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X0_TLS_GD_HA 72 /* X0 pipe ha() 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X1_TLS_GD_HA 73 /* X1 pipe ha() 16-bit TLS GD offset */
-#define R_TILEPRO_IMM16_X0_TLS_IE 74 /* X0 pipe 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X1_TLS_IE 75 /* X1 pipe 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X0_TLS_IE_LO 76 /* X0 pipe low 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X1_TLS_IE_LO 77 /* X1 pipe low 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X0_TLS_IE_HI 78 /* X0 pipe high 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X1_TLS_IE_HI 79 /* X1 pipe high 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X0_TLS_IE_HA 80 /* X0 pipe ha() 16-bit TLS IE offset */
-#define R_TILEPRO_IMM16_X1_TLS_IE_HA 81 /* X1 pipe ha() 16-bit TLS IE offset */
-#define R_TILEPRO_TLS_DTPMOD32 82 /* ID of module containing symbol */
-#define R_TILEPRO_TLS_DTPOFF32 83 /* Offset in TLS block */
-#define R_TILEPRO_TLS_TPOFF32 84 /* Offset in static TLS block */
-#define R_TILEPRO_IMM16_X0_TLS_LE 85 /* X0 pipe 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X1_TLS_LE 86 /* X1 pipe 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X0_TLS_LE_LO 87 /* X0 pipe low 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X1_TLS_LE_LO 88 /* X1 pipe low 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X0_TLS_LE_HI 89 /* X0 pipe high 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X1_TLS_LE_HI 90 /* X1 pipe high 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X0_TLS_LE_HA 91 /* X0 pipe ha() 16-bit TLS LE offset */
-#define R_TILEPRO_IMM16_X1_TLS_LE_HA 92 /* X1 pipe ha() 16-bit TLS LE offset */
-
-#define R_TILEPRO_GNU_VTINHERIT 128 /* GNU C++ vtable hierarchy */
-#define R_TILEPRO_GNU_VTENTRY 129 /* GNU C++ vtable member usage */
-
-#define R_TILEPRO_NUM 130
-
-
-/* TILE-Gx relocations. */
-#define R_TILEGX_NONE 0 /* No reloc */
-#define R_TILEGX_64 1 /* Direct 64 bit */
-#define R_TILEGX_32 2 /* Direct 32 bit */
-#define R_TILEGX_16 3 /* Direct 16 bit */
-#define R_TILEGX_8 4 /* Direct 8 bit */
-#define R_TILEGX_64_PCREL 5 /* PC relative 64 bit */
-#define R_TILEGX_32_PCREL 6 /* PC relative 32 bit */
-#define R_TILEGX_16_PCREL 7 /* PC relative 16 bit */
-#define R_TILEGX_8_PCREL 8 /* PC relative 8 bit */
-#define R_TILEGX_HW0 9 /* hword 0 16-bit */
-#define R_TILEGX_HW1 10 /* hword 1 16-bit */
-#define R_TILEGX_HW2 11 /* hword 2 16-bit */
-#define R_TILEGX_HW3 12 /* hword 3 16-bit */
-#define R_TILEGX_HW0_LAST 13 /* last hword 0 16-bit */
-#define R_TILEGX_HW1_LAST 14 /* last hword 1 16-bit */
-#define R_TILEGX_HW2_LAST 15 /* last hword 2 16-bit */
-#define R_TILEGX_COPY 16 /* Copy relocation */
-#define R_TILEGX_GLOB_DAT 17 /* Create GOT entry */
-#define R_TILEGX_JMP_SLOT 18 /* Create PLT entry */
-#define R_TILEGX_RELATIVE 19 /* Adjust by program base */
-#define R_TILEGX_BROFF_X1 20 /* X1 pipe branch offset */
-#define R_TILEGX_JUMPOFF_X1 21 /* X1 pipe jump offset */
-#define R_TILEGX_JUMPOFF_X1_PLT 22 /* X1 pipe jump offset to PLT */
-#define R_TILEGX_IMM8_X0 23 /* X0 pipe 8-bit */
-#define R_TILEGX_IMM8_Y0 24 /* Y0 pipe 8-bit */
-#define R_TILEGX_IMM8_X1 25 /* X1 pipe 8-bit */
-#define R_TILEGX_IMM8_Y1 26 /* Y1 pipe 8-bit */
-#define R_TILEGX_DEST_IMM8_X1 27 /* X1 pipe destination 8-bit */
-#define R_TILEGX_MT_IMM14_X1 28 /* X1 pipe mtspr */
-#define R_TILEGX_MF_IMM14_X1 29 /* X1 pipe mfspr */
-#define R_TILEGX_MMSTART_X0 30 /* X0 pipe mm "start" */
-#define R_TILEGX_MMEND_X0 31 /* X0 pipe mm "end" */
-#define R_TILEGX_SHAMT_X0 32 /* X0 pipe shift amount */
-#define R_TILEGX_SHAMT_X1 33 /* X1 pipe shift amount */
-#define R_TILEGX_SHAMT_Y0 34 /* Y0 pipe shift amount */
-#define R_TILEGX_SHAMT_Y1 35 /* Y1 pipe shift amount */
-#define R_TILEGX_IMM16_X0_HW0 36 /* X0 pipe hword 0 */
-#define R_TILEGX_IMM16_X1_HW0 37 /* X1 pipe hword 0 */
-#define R_TILEGX_IMM16_X0_HW1 38 /* X0 pipe hword 1 */
-#define R_TILEGX_IMM16_X1_HW1 39 /* X1 pipe hword 1 */
-#define R_TILEGX_IMM16_X0_HW2 40 /* X0 pipe hword 2 */
-#define R_TILEGX_IMM16_X1_HW2 41 /* X1 pipe hword 2 */
-#define R_TILEGX_IMM16_X0_HW3 42 /* X0 pipe hword 3 */
-#define R_TILEGX_IMM16_X1_HW3 43 /* X1 pipe hword 3 */
-#define R_TILEGX_IMM16_X0_HW0_LAST 44 /* X0 pipe last hword 0 */
-#define R_TILEGX_IMM16_X1_HW0_LAST 45 /* X1 pipe last hword 0 */
-#define R_TILEGX_IMM16_X0_HW1_LAST 46 /* X0 pipe last hword 1 */
-#define R_TILEGX_IMM16_X1_HW1_LAST 47 /* X1 pipe last hword 1 */
-#define R_TILEGX_IMM16_X0_HW2_LAST 48 /* X0 pipe last hword 2 */
-#define R_TILEGX_IMM16_X1_HW2_LAST 49 /* X1 pipe last hword 2 */
-#define R_TILEGX_IMM16_X0_HW0_PCREL 50 /* X0 pipe PC relative hword 0 */
-#define R_TILEGX_IMM16_X1_HW0_PCREL 51 /* X1 pipe PC relative hword 0 */
-#define R_TILEGX_IMM16_X0_HW1_PCREL 52 /* X0 pipe PC relative hword 1 */
-#define R_TILEGX_IMM16_X1_HW1_PCREL 53 /* X1 pipe PC relative hword 1 */
-#define R_TILEGX_IMM16_X0_HW2_PCREL 54 /* X0 pipe PC relative hword 2 */
-#define R_TILEGX_IMM16_X1_HW2_PCREL 55 /* X1 pipe PC relative hword 2 */
-#define R_TILEGX_IMM16_X0_HW3_PCREL 56 /* X0 pipe PC relative hword 3 */
-#define R_TILEGX_IMM16_X1_HW3_PCREL 57 /* X1 pipe PC relative hword 3 */
-#define R_TILEGX_IMM16_X0_HW0_LAST_PCREL 58 /* X0 pipe PC-rel last hword 0 */
-#define R_TILEGX_IMM16_X1_HW0_LAST_PCREL 59 /* X1 pipe PC-rel last hword 0 */
-#define R_TILEGX_IMM16_X0_HW1_LAST_PCREL 60 /* X0 pipe PC-rel last hword 1 */
-#define R_TILEGX_IMM16_X1_HW1_LAST_PCREL 61 /* X1 pipe PC-rel last hword 1 */
-#define R_TILEGX_IMM16_X0_HW2_LAST_PCREL 62 /* X0 pipe PC-rel last hword 2 */
-#define R_TILEGX_IMM16_X1_HW2_LAST_PCREL 63 /* X1 pipe PC-rel last hword 2 */
-#define R_TILEGX_IMM16_X0_HW0_GOT 64 /* X0 pipe hword 0 GOT offset */
-#define R_TILEGX_IMM16_X1_HW0_GOT 65 /* X1 pipe hword 0 GOT offset */
-#define R_TILEGX_IMM16_X0_HW0_PLT_PCREL 66 /* X0 pipe PC-rel PLT hword 0 */
-#define R_TILEGX_IMM16_X1_HW0_PLT_PCREL 67 /* X1 pipe PC-rel PLT hword 0 */
-#define R_TILEGX_IMM16_X0_HW1_PLT_PCREL 68 /* X0 pipe PC-rel PLT hword 1 */
-#define R_TILEGX_IMM16_X1_HW1_PLT_PCREL 69 /* X1 pipe PC-rel PLT hword 1 */
-#define R_TILEGX_IMM16_X0_HW2_PLT_PCREL 70 /* X0 pipe PC-rel PLT hword 2 */
-#define R_TILEGX_IMM16_X1_HW2_PLT_PCREL 71 /* X1 pipe PC-rel PLT hword 2 */
-#define R_TILEGX_IMM16_X0_HW0_LAST_GOT 72 /* X0 pipe last hword 0 GOT offset */
-#define R_TILEGX_IMM16_X1_HW0_LAST_GOT 73 /* X1 pipe last hword 0 GOT offset */
-#define R_TILEGX_IMM16_X0_HW1_LAST_GOT 74 /* X0 pipe last hword 1 GOT offset */
-#define R_TILEGX_IMM16_X1_HW1_LAST_GOT 75 /* X1 pipe last hword 1 GOT offset */
-#define R_TILEGX_IMM16_X0_HW3_PLT_PCREL 76 /* X0 pipe PC-rel PLT hword 3 */
-#define R_TILEGX_IMM16_X1_HW3_PLT_PCREL 77 /* X1 pipe PC-rel PLT hword 3 */
-#define R_TILEGX_IMM16_X0_HW0_TLS_GD 78 /* X0 pipe hword 0 TLS GD offset */
-#define R_TILEGX_IMM16_X1_HW0_TLS_GD 79 /* X1 pipe hword 0 TLS GD offset */
-#define R_TILEGX_IMM16_X0_HW0_TLS_LE 80 /* X0 pipe hword 0 TLS LE offset */
-#define R_TILEGX_IMM16_X1_HW0_TLS_LE 81 /* X1 pipe hword 0 TLS LE offset */
-#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_LE 82 /* X0 pipe last hword 0 LE off */
-#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_LE 83 /* X1 pipe last hword 0 LE off */
-#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_LE 84 /* X0 pipe last hword 1 LE off */
-#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_LE 85 /* X1 pipe last hword 1 LE off */
-#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_GD 86 /* X0 pipe last hword 0 GD off */
-#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_GD 87 /* X1 pipe last hword 0 GD off */
-#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_GD 88 /* X0 pipe last hword 1 GD off */
-#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_GD 89 /* X1 pipe last hword 1 GD off */
-/* Relocs 90-91 are currently not defined. */
-#define R_TILEGX_IMM16_X0_HW0_TLS_IE 92 /* X0 pipe hword 0 TLS IE offset */
-#define R_TILEGX_IMM16_X1_HW0_TLS_IE 93 /* X1 pipe hword 0 TLS IE offset */
-#define R_TILEGX_IMM16_X0_HW0_LAST_PLT_PCREL 94 /* X0 pipe PC-rel PLT last hword 0 */
-#define R_TILEGX_IMM16_X1_HW0_LAST_PLT_PCREL 95 /* X1 pipe PC-rel PLT last hword 0 */
-#define R_TILEGX_IMM16_X0_HW1_LAST_PLT_PCREL 96 /* X0 pipe PC-rel PLT last hword 1 */
-#define R_TILEGX_IMM16_X1_HW1_LAST_PLT_PCREL 97 /* X1 pipe PC-rel PLT last hword 1 */
-#define R_TILEGX_IMM16_X0_HW2_LAST_PLT_PCREL 98 /* X0 pipe PC-rel PLT last hword 2 */
-#define R_TILEGX_IMM16_X1_HW2_LAST_PLT_PCREL 99 /* X1 pipe PC-rel PLT last hword 2 */
-#define R_TILEGX_IMM16_X0_HW0_LAST_TLS_IE 100 /* X0 pipe last hword 0 IE off */
-#define R_TILEGX_IMM16_X1_HW0_LAST_TLS_IE 101 /* X1 pipe last hword 0 IE off */
-#define R_TILEGX_IMM16_X0_HW1_LAST_TLS_IE 102 /* X0 pipe last hword 1 IE off */
-#define R_TILEGX_IMM16_X1_HW1_LAST_TLS_IE 103 /* X1 pipe last hword 1 IE off */
-/* Relocs 104-105 are currently not defined. */
-#define R_TILEGX_TLS_DTPMOD64 106 /* 64-bit ID of symbol's module */
-#define R_TILEGX_TLS_DTPOFF64 107 /* 64-bit offset in TLS block */
-#define R_TILEGX_TLS_TPOFF64 108 /* 64-bit offset in static TLS block */
-#define R_TILEGX_TLS_DTPMOD32 109 /* 32-bit ID of symbol's module */
-#define R_TILEGX_TLS_DTPOFF32 110 /* 32-bit offset in TLS block */
-#define R_TILEGX_TLS_TPOFF32 111 /* 32-bit offset in static TLS block */
-#define R_TILEGX_TLS_GD_CALL 112 /* "jal" for TLS GD */
-#define R_TILEGX_IMM8_X0_TLS_GD_ADD 113 /* X0 pipe "addi" for TLS GD */
-#define R_TILEGX_IMM8_X1_TLS_GD_ADD 114 /* X1 pipe "addi" for TLS GD */
-#define R_TILEGX_IMM8_Y0_TLS_GD_ADD 115 /* Y0 pipe "addi" for TLS GD */
-#define R_TILEGX_IMM8_Y1_TLS_GD_ADD 116 /* Y1 pipe "addi" for TLS GD */
-#define R_TILEGX_TLS_IE_LOAD 117 /* "ld_tls" for TLS IE */
-#define R_TILEGX_IMM8_X0_TLS_ADD 118 /* X0 pipe "addi" for TLS GD/IE */
-#define R_TILEGX_IMM8_X1_TLS_ADD 119 /* X1 pipe "addi" for TLS GD/IE */
-#define R_TILEGX_IMM8_Y0_TLS_ADD 120 /* Y0 pipe "addi" for TLS GD/IE */
-#define R_TILEGX_IMM8_Y1_TLS_ADD 121 /* Y1 pipe "addi" for TLS GD/IE */
-
-#define R_TILEGX_GNU_VTINHERIT 128 /* GNU C++ vtable hierarchy */
-#define R_TILEGX_GNU_VTENTRY 129 /* GNU C++ vtable member usage */
-
-#define R_TILEGX_NUM 130
-
-/* BPF specific declarations. */
-
-#define R_BPF_NONE 0 /* No reloc */
-#define R_BPF_MAP_FD 1 /* Map fd to pointer */
-
-/* Imagination Meta specific relocations. */
-
-#define R_METAG_HIADDR16 0
-#define R_METAG_LOADDR16 1
-#define R_METAG_ADDR32 2 /* 32bit absolute address */
-#define R_METAG_NONE 3 /* No reloc */
-#define R_METAG_RELBRANCH 4
-#define R_METAG_GETSETOFF 5
-
-/* Backward compatability */
-#define R_METAG_REG32OP1 6
-#define R_METAG_REG32OP2 7
-#define R_METAG_REG32OP3 8
-#define R_METAG_REG16OP1 9
-#define R_METAG_REG16OP2 10
-#define R_METAG_REG16OP3 11
-#define R_METAG_REG32OP4 12
-
-#define R_METAG_HIOG 13
-#define R_METAG_LOOG 14
-
-#define R_METAG_REL8 15
-#define R_METAG_REL16 16
-
-/* GNU */
-#define R_METAG_GNU_VTINHERIT 30
-#define R_METAG_GNU_VTENTRY 31
-
-/* PIC relocations */
-#define R_METAG_HI16_GOTOFF 32
-#define R_METAG_LO16_GOTOFF 33
-#define R_METAG_GETSET_GOTOFF 34
-#define R_METAG_GETSET_GOT 35
-#define R_METAG_HI16_GOTPC 36
-#define R_METAG_LO16_GOTPC 37
-#define R_METAG_HI16_PLT 38
-#define R_METAG_LO16_PLT 39
-#define R_METAG_RELBRANCH_PLT 40
-#define R_METAG_GOTOFF 41
-#define R_METAG_PLT 42
-#define R_METAG_COPY 43
-#define R_METAG_JMP_SLOT 44
-#define R_METAG_RELATIVE 45
-#define R_METAG_GLOB_DAT 46
-
-/* TLS relocations */
-#define R_METAG_TLS_GD 47
-#define R_METAG_TLS_LDM 48
-#define R_METAG_TLS_LDO_HI16 49
-#define R_METAG_TLS_LDO_LO16 50
-#define R_METAG_TLS_LDO 51
-#define R_METAG_TLS_IE 52
-#define R_METAG_TLS_IENONPIC 53
-#define R_METAG_TLS_IENONPIC_HI16 54
-#define R_METAG_TLS_IENONPIC_LO16 55
-#define R_METAG_TLS_TPOFF 56
-#define R_METAG_TLS_DTPMOD 57
-#define R_METAG_TLS_DTPOFF 58
-#define R_METAG_TLS_LE 59
-#define R_METAG_TLS_LE_HI16 60
-#define R_METAG_TLS_LE_LO16 61
-
-__END_DECLS
-
-#endif /* elf.h */
diff --git a/elf/enbl-secure.c b/elf/enbl-secure.c
deleted file mode 100644
index c0723774d9..0000000000
--- a/elf/enbl-secure.c
+++ /dev/null
@@ -1,36 +0,0 @@
-/* Define and initialize the `__libc_enable_secure' flag. Generic version.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file is used in the static libc. For the shared library,
- dl-sysdep.c defines and initializes __libc_enable_secure. */
-
-#include <unistd.h>
-#include <libc-internal.h>
-
-/* If nonzero __libc_enable_secure is already set. */
-int __libc_enable_secure_decided;
-/* Safest assumption, if somehow the initializer isn't run. */
-int __libc_enable_secure = 1;
-
-void
-__libc_init_secure (void)
-{
- if (__libc_enable_secure_decided == 0)
- __libc_enable_secure = (__geteuid () != __getuid ()
- || __getegid () != __getgid ());
-}
diff --git a/elf/failobj.c b/elf/failobj.c
deleted file mode 100644
index 500606382e..0000000000
--- a/elf/failobj.c
+++ /dev/null
@@ -1,10 +0,0 @@
-/* This function is supposed to not exist. */
-extern int xyzzy (int);
-
-extern int foo (int);
-
-int
-foo (int a)
-{
- return xyzzy (a);
-}
diff --git a/elf/filter.c b/elf/filter.c
deleted file mode 100644
index 46aa15ba16..0000000000
--- a/elf/filter.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include <mcheck.h>
-#include <stdio.h>
-#include <string.h>
-
-extern const char *foo (void);
-
-int
-main (void)
-{
- const char *s;
-
- mtrace ();
-
- s = foo ();
-
- printf ("called `foo' from `%s'\n", s);
-
- return strcmp (s, "filtmod2.c");
-}
diff --git a/elf/filtmod1.c b/elf/filtmod1.c
deleted file mode 100644
index 1d9b19481d..0000000000
--- a/elf/filtmod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern const char *foo (void);
-
-const char *
-foo (void)
-{
- return __FILE__;
-}
diff --git a/elf/filtmod2.c b/elf/filtmod2.c
deleted file mode 100644
index 1d9b19481d..0000000000
--- a/elf/filtmod2.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern const char *foo (void);
-
-const char *
-foo (void)
-{
- return __FILE__;
-}
diff --git a/elf/firstobj.c b/elf/firstobj.c
deleted file mode 100644
index 2e6033eab6..0000000000
--- a/elf/firstobj.c
+++ /dev/null
@@ -1,10 +0,0 @@
-#include <errno.h>
-
-extern int foo (void);
-
-int
-foo (void)
-{
- errno = 0;
- return 0;
-}
diff --git a/elf/gen-trusted-dirs.awk b/elf/gen-trusted-dirs.awk
deleted file mode 100644
index 59f10a4856..0000000000
--- a/elf/gen-trusted-dirs.awk
+++ /dev/null
@@ -1,37 +0,0 @@
-BEGIN {
- FS = " ";
-}
-
-{
- for (i = 1; i <= NF; ++i) {
- s[cnt++] = $i"/";
- }
-}
-
-END {
- printf ("#define SYSTEM_DIRS \\\n");
-
- printf (" \"%s\"", s[0]);
-
- for (i = 1; i < cnt; ++i) {
- printf (" \"\\0\" \"%s\"", s[i]);
- }
-
- printf ("\n\n");
-
- printf ("#define SYSTEM_DIRS_LEN \\\n");
-
- printf (" %d", length (s[0]));
- m = length (s[0]);
-
- for (i = 1; i < cnt; ++i) {
- printf (", %d", length(s[i]));
- if (length(s[i]) > m) {
- m = length(s[i]);
- }
- }
-
- printf ("\n\n");
-
- printf ("#define SYSTEM_DIRS_MAX_LEN\t%d\n", m);
-}
diff --git a/elf/genrtldtbl.awk b/elf/genrtldtbl.awk
deleted file mode 100644
index 0e2a374901..0000000000
--- a/elf/genrtldtbl.awk
+++ /dev/null
@@ -1,29 +0,0 @@
-#!/usr/bin/awk
-BEGIN {
- FS=":";
- count=0;
-}
-{
- for (i = 1; i <= NF; ++i) {
- gsub (/\/*$/, "", $i);
- dir[count++] = $i;
- }
-}
-END {
- for (i = 0; i < count; ++i) {
- printf ("static struct r_search_path_elem rtld_search_dir%d =\n", i+1);
- printf (" { \"%s/\", %d, unknown, 0, nonexisting, NULL, NULL, ",
- dir[i], length (dir[i]) + 1);
- if (i== 0)
- printf ("NULL };\n");
- else
- printf ("&rtld_search_dir%d };\n", i);
- }
- printf ("\nstatic struct r_search_path_elem *rtld_search_dirs[] =\n{\n");
- for (i = 0; i < count; ++i) {
- printf (" &rtld_search_dir%d,\n", i + 1);
- }
- printf (" NULL\n};\n\n");
- printf ("static struct r_search_path_elem *all_dirs = &rtld_search_dir%d;\n",
- count);
-}
diff --git a/elf/get-dynamic-info.h b/elf/get-dynamic-info.h
deleted file mode 100644
index 7525c3a5b2..0000000000
--- a/elf/get-dynamic-info.h
+++ /dev/null
@@ -1,184 +0,0 @@
-/* Read the dynamic section at DYN and fill in INFO with indices DT_*.
- Copyright (C) 2012-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file is included multiple times and therefore lacks a header
- file inclusion guard. */
-
-#include <assert.h>
-#include <libc-diag.h>
-
-#ifndef RESOLVE_MAP
-static
-#else
-auto
-#endif
-inline void __attribute__ ((unused, always_inline))
-elf_get_dynamic_info (struct link_map *l, ElfW(Dyn) *temp)
-{
- ElfW(Dyn) *dyn = l->l_ld;
- ElfW(Dyn) **info;
-#if __ELF_NATIVE_CLASS == 32
- typedef Elf32_Word d_tag_utype;
-#elif __ELF_NATIVE_CLASS == 64
- typedef Elf64_Xword d_tag_utype;
-#endif
-
-#ifndef RTLD_BOOTSTRAP
- if (dyn == NULL)
- return;
-#endif
-
- info = l->l_info;
-
- while (dyn->d_tag != DT_NULL)
- {
- if ((d_tag_utype) dyn->d_tag < DT_NUM)
- info[dyn->d_tag] = dyn;
- else if (dyn->d_tag >= DT_LOPROC &&
- dyn->d_tag < DT_LOPROC + DT_THISPROCNUM)
- {
- /* This does not violate the array bounds of l->l_info, but
- gcc 4.6 on sparc somehow does not see this. */
- DIAG_PUSH_NEEDS_COMMENT;
- DIAG_IGNORE_NEEDS_COMMENT (4.6,
- "-Warray-bounds");
- info[dyn->d_tag - DT_LOPROC + DT_NUM] = dyn;
- DIAG_POP_NEEDS_COMMENT;
- }
- else if ((d_tag_utype) DT_VERSIONTAGIDX (dyn->d_tag) < DT_VERSIONTAGNUM)
- info[VERSYMIDX (dyn->d_tag)] = dyn;
- else if ((d_tag_utype) DT_EXTRATAGIDX (dyn->d_tag) < DT_EXTRANUM)
- info[DT_EXTRATAGIDX (dyn->d_tag) + DT_NUM + DT_THISPROCNUM
- + DT_VERSIONTAGNUM] = dyn;
- else if ((d_tag_utype) DT_VALTAGIDX (dyn->d_tag) < DT_VALNUM)
- info[DT_VALTAGIDX (dyn->d_tag) + DT_NUM + DT_THISPROCNUM
- + DT_VERSIONTAGNUM + DT_EXTRANUM] = dyn;
- else if ((d_tag_utype) DT_ADDRTAGIDX (dyn->d_tag) < DT_ADDRNUM)
- info[DT_ADDRTAGIDX (dyn->d_tag) + DT_NUM + DT_THISPROCNUM
- + DT_VERSIONTAGNUM + DT_EXTRANUM + DT_VALNUM] = dyn;
- ++dyn;
- }
-
-#define DL_RO_DYN_TEMP_CNT 8
-
-#ifndef DL_RO_DYN_SECTION
- /* Don't adjust .dynamic unnecessarily. */
- if (l->l_addr != 0)
- {
- ElfW(Addr) l_addr = l->l_addr;
- int cnt = 0;
-
-# define ADJUST_DYN_INFO(tag) \
- do \
- if (info[tag] != NULL) \
- { \
- if (temp) \
- { \
- temp[cnt].d_tag = info[tag]->d_tag; \
- temp[cnt].d_un.d_ptr = info[tag]->d_un.d_ptr + l_addr; \
- info[tag] = temp + cnt++; \
- } \
- else \
- info[tag]->d_un.d_ptr += l_addr; \
- } \
- while (0)
-
- ADJUST_DYN_INFO (DT_HASH);
- ADJUST_DYN_INFO (DT_PLTGOT);
- ADJUST_DYN_INFO (DT_STRTAB);
- ADJUST_DYN_INFO (DT_SYMTAB);
-# if ! ELF_MACHINE_NO_RELA
- ADJUST_DYN_INFO (DT_RELA);
-# endif
-# if ! ELF_MACHINE_NO_REL
- ADJUST_DYN_INFO (DT_REL);
-# endif
- ADJUST_DYN_INFO (DT_JMPREL);
- ADJUST_DYN_INFO (VERSYMIDX (DT_VERSYM));
- ADJUST_DYN_INFO (DT_ADDRTAGIDX (DT_GNU_HASH) + DT_NUM + DT_THISPROCNUM
- + DT_VERSIONTAGNUM + DT_EXTRANUM + DT_VALNUM);
-# undef ADJUST_DYN_INFO
- assert (cnt <= DL_RO_DYN_TEMP_CNT);
- }
-#endif
- if (info[DT_PLTREL] != NULL)
- {
-#if ELF_MACHINE_NO_RELA
- assert (info[DT_PLTREL]->d_un.d_val == DT_REL);
-#elif ELF_MACHINE_NO_REL
- assert (info[DT_PLTREL]->d_un.d_val == DT_RELA);
-#else
- assert (info[DT_PLTREL]->d_un.d_val == DT_REL
- || info[DT_PLTREL]->d_un.d_val == DT_RELA);
-#endif
- }
-#if ! ELF_MACHINE_NO_RELA
- if (info[DT_RELA] != NULL)
- assert (info[DT_RELAENT]->d_un.d_val == sizeof (ElfW(Rela)));
-# endif
-# if ! ELF_MACHINE_NO_REL
- if (info[DT_REL] != NULL)
- assert (info[DT_RELENT]->d_un.d_val == sizeof (ElfW(Rel)));
-#endif
-#ifdef RTLD_BOOTSTRAP
- /* Only the bind now flags are allowed. */
- assert (info[VERSYMIDX (DT_FLAGS_1)] == NULL
- || (info[VERSYMIDX (DT_FLAGS_1)]->d_un.d_val & ~DF_1_NOW) == 0);
- assert (info[DT_FLAGS] == NULL
- || (info[DT_FLAGS]->d_un.d_val & ~DF_BIND_NOW) == 0);
- /* Flags must not be set for ld.so. */
- assert (info[DT_RUNPATH] == NULL);
- assert (info[DT_RPATH] == NULL);
-#else
- if (info[DT_FLAGS] != NULL)
- {
- /* Flags are used. Translate to the old form where available.
- Since these l_info entries are only tested for NULL pointers it
- is ok if they point to the DT_FLAGS entry. */
- l->l_flags = info[DT_FLAGS]->d_un.d_val;
-
- if (l->l_flags & DF_SYMBOLIC)
- info[DT_SYMBOLIC] = info[DT_FLAGS];
- if (l->l_flags & DF_TEXTREL)
- info[DT_TEXTREL] = info[DT_FLAGS];
- if (l->l_flags & DF_BIND_NOW)
- info[DT_BIND_NOW] = info[DT_FLAGS];
- }
- if (info[VERSYMIDX (DT_FLAGS_1)] != NULL)
- {
- l->l_flags_1 = info[VERSYMIDX (DT_FLAGS_1)]->d_un.d_val;
-
- /* Only DT_1_SUPPORTED_MASK bits are supported, and we would like
- to assert this, but we can't. Users have been setting
- unsupported DF_1_* flags for a long time and glibc has ignored
- them. Therefore to avoid breaking existing applications the
- best we can do is add a warning during debugging with the
- intent of notifying the user of the problem. */
- if (__builtin_expect (GLRO(dl_debug_mask) & DL_DEBUG_FILES, 0)
- && l->l_flags_1 & ~DT_1_SUPPORTED_MASK)
- _dl_debug_printf ("\nWARNING: Unsupported flag value(s) of 0x%x in DT_FLAGS_1.\n",
- l->l_flags_1 & ~DT_1_SUPPORTED_MASK);
-
- if (l->l_flags_1 & DF_1_NOW)
- info[DT_BIND_NOW] = info[VERSYMIDX (DT_FLAGS_1)];
- }
- if (info[DT_RUNPATH] != NULL)
- /* If both RUNPATH and RPATH are given, the latter is ignored. */
- info[DT_RPATH] = NULL;
-#endif
-}
diff --git a/elf/global.c b/elf/global.c
deleted file mode 100644
index c675858b64..0000000000
--- a/elf/global.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int test (void);
-
-int
-main (void)
-{
- return test ();
-}
diff --git a/elf/globalmod1.c b/elf/globalmod1.c
deleted file mode 100644
index 3f80822269..0000000000
--- a/elf/globalmod1.c
+++ /dev/null
@@ -1,17 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-extern int test (void);
-
-int
-test (void)
-{
- (void) dlopen ("reldepmod4.so", RTLD_LAZY | RTLD_GLOBAL);
- if (dlsym (RTLD_DEFAULT, "call_me") != NULL)
- {
- puts ("found \"call_me\"");
- return 0;
- }
- puts ("didn't find \"call_me\"");
- return 1;
-}
diff --git a/elf/ifuncdep1.c b/elf/ifuncdep1.c
deleted file mode 100644
index 77d663dcec..0000000000
--- a/elf/ifuncdep1.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols without -fPIC. */
-
-#include "ifuncmod1.c"
diff --git a/elf/ifuncdep1pic.c b/elf/ifuncdep1pic.c
deleted file mode 100644
index b6381e4868..0000000000
--- a/elf/ifuncdep1pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmod1.c"
diff --git a/elf/ifuncdep2.c b/elf/ifuncdep2.c
deleted file mode 100644
index d87d61d5be..0000000000
--- a/elf/ifuncdep2.c
+++ /dev/null
@@ -1,59 +0,0 @@
-/* Test 3 STT_GNU_IFUNC symbols. */
-
-#include "ifunc-sel.h"
-
-int global = -1;
-/* Can't use __attribute__((visibility("protected"))) until the GCC bug:
-
- https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65248
-
- is fixed. */
-asm (".protected global");
-
-static int
-one (void)
-{
- return 1;
-}
-
-static int
-minus_one (void)
-{
- return -1;
-}
-
-static int
-zero (void)
-{
- return 0;
-}
-
-void * foo1_ifunc (void) __asm__ ("foo1");
-__asm__(".type foo1, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo1_ifunc (void)
-{
- return ifunc_sel (one, minus_one, zero);
-}
-
-void * foo2_ifunc (void) __asm__ ("foo2");
-__asm__(".type foo2, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo2_ifunc (void)
-{
- return ifunc_sel (minus_one, one, zero);
-}
-
-void * foo3_ifunc (void) __asm__ ("foo3");
-__asm__(".type foo3, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo3_ifunc (void)
-{
- return ifunc_sel (one, zero, minus_one);
-}
diff --git a/elf/ifuncdep2pic.c b/elf/ifuncdep2pic.c
deleted file mode 100644
index a84253dbc4..0000000000
--- a/elf/ifuncdep2pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncdep2.c"
diff --git a/elf/ifuncdep5.c b/elf/ifuncdep5.c
deleted file mode 100644
index f26234336e..0000000000
--- a/elf/ifuncdep5.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols without -fPIC. */
-
-#include "ifuncmod5.c"
diff --git a/elf/ifuncdep5pic.c b/elf/ifuncdep5pic.c
deleted file mode 100644
index 3edb3a07c6..0000000000
--- a/elf/ifuncdep5pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmod5.c"
diff --git a/elf/ifuncmain1.c b/elf/ifuncmain1.c
deleted file mode 100644
index 747fc02648..0000000000
--- a/elf/ifuncmain1.c
+++ /dev/null
@@ -1,64 +0,0 @@
-/* Test STT_GNU_IFUNC symbols:
-
- 1. Direct function call.
- 2. Function pointer.
- 3. Visibility without override.
- */
-
-#include <stdlib.h>
-
-int ret_foo;
-int ret_foo_hidden;
-int ret_foo_protected;
-
-extern int foo (void);
-extern int foo_protected (void);
-
-#ifndef FOO_P
-typedef int (*foo_p) (void);
-#endif
-
-foo_p foo_ptr = foo;
-foo_p foo_procted_ptr = foo_protected;
-
-extern foo_p get_foo_p (void);
-extern foo_p get_foo_hidden_p (void);
-extern foo_p get_foo_protected_p (void);
-
-int
-main (void)
-{
- foo_p p;
-
- if (foo_ptr != foo)
- abort ();
- if (foo () != -1)
- abort ();
- if ((*foo_ptr) () != -1)
- abort ();
-
- if (foo_procted_ptr != foo_protected)
- abort ();
- if (foo_protected () != 0)
- abort ();
- if ((*foo_procted_ptr) () != 0)
- abort ();
-
- p = get_foo_p ();
- if (p != foo)
- abort ();
- if (ret_foo != -1 || (*p) () != ret_foo)
- abort ();
-
- p = get_foo_hidden_p ();
- if (ret_foo_hidden != 1 || (*p) () != ret_foo_hidden)
- abort ();
-
- p = get_foo_protected_p ();
- if (p != foo_protected)
- abort ();
- if (ret_foo_protected != 0 || (*p) () != ret_foo_protected)
- abort ();
-
- return 0;
-}
diff --git a/elf/ifuncmain1pic.c b/elf/ifuncmain1pic.c
deleted file mode 100644
index db19dc9678..0000000000
--- a/elf/ifuncmain1pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1picstatic.c b/elf/ifuncmain1picstatic.c
deleted file mode 100644
index c937933029..0000000000
--- a/elf/ifuncmain1picstatic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and -static. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1pie.c b/elf/ifuncmain1pie.c
deleted file mode 100644
index c16ef6dd09..0000000000
--- a/elf/ifuncmain1pie.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with PIE. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1static.c b/elf/ifuncmain1static.c
deleted file mode 100644
index fdd1e09024..0000000000
--- a/elf/ifuncmain1static.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -static. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1staticpic.c b/elf/ifuncmain1staticpic.c
deleted file mode 100644
index 39e0cbb4b8..0000000000
--- a/elf/ifuncmain1staticpic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and no DSO. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1staticpie.c b/elf/ifuncmain1staticpie.c
deleted file mode 100644
index 4891114260..0000000000
--- a/elf/ifuncmain1staticpie.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with PIE and no DSO. */
-
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain1vis.c b/elf/ifuncmain1vis.c
deleted file mode 100644
index d35e2f81fc..0000000000
--- a/elf/ifuncmain1vis.c
+++ /dev/null
@@ -1,87 +0,0 @@
-/* Test STT_GNU_IFUNC symbols:
-
- 1. Direct function call.
- 2. Function pointer.
- 3. Visibility with override.
- */
-
-#include <stdlib.h>
-
-int ret_foo;
-int ret_foo_hidden;
-int ret_foo_protected;
-
-extern int foo (void);
-extern int foo_protected (void);
-
-#ifndef FOO_P
-typedef int (*foo_p) (void);
-#endif
-
-foo_p foo_ptr = foo;
-foo_p foo_procted_ptr = foo_protected;
-
-extern foo_p get_foo_p (void);
-extern foo_p get_foo_hidden_p (void);
-extern foo_p get_foo_protected_p (void);
-
-int
-__attribute__ ((noinline))
-foo (void)
-{
- return -30;
-}
-
-int
-__attribute__ ((noinline))
-foo_hidden (void)
-{
- return -20;
-}
-
-int
-__attribute__ ((noinline))
-foo_protected (void)
-{
- return -40;
-}
-
-int
-main (void)
-{
- foo_p p;
-
- if (foo_ptr != foo)
- abort ();
- if ((*foo_ptr) () != -30)
- abort ();
-
- if (foo_procted_ptr != foo_protected)
- abort ();
- if ((*foo_procted_ptr) () != -40)
- abort ();
-
- p = get_foo_p ();
- if (p != foo)
- abort ();
- if (foo () != -30)
- abort ();
- if (ret_foo != -30 || (*p) () != ret_foo)
- abort ();
-
- p = get_foo_hidden_p ();
- if (foo_hidden () != -20)
- abort ();
- if (ret_foo_hidden != 1 || (*p) () != ret_foo_hidden)
- abort ();
-
- p = get_foo_protected_p ();
- if (p == foo_protected)
- abort ();
- if (foo_protected () != -40)
- abort ();
- if (ret_foo_protected != 0 || (*p) () != ret_foo_protected)
- abort ();
-
- return 0;
-}
diff --git a/elf/ifuncmain1vispic.c b/elf/ifuncmain1vispic.c
deleted file mode 100644
index f8c104d560..0000000000
--- a/elf/ifuncmain1vispic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmain1vis.c"
diff --git a/elf/ifuncmain1vispie.c b/elf/ifuncmain1vispie.c
deleted file mode 100644
index ad06d2ba1c..0000000000
--- a/elf/ifuncmain1vispie.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with PIE. */
-
-#include "ifuncmain1vis.c"
diff --git a/elf/ifuncmain2.c b/elf/ifuncmain2.c
deleted file mode 100644
index db3ba56a02..0000000000
--- a/elf/ifuncmain2.c
+++ /dev/null
@@ -1,14 +0,0 @@
-/* Test calling one STT_GNU_IFUNC function with 3 different
- STT_GNU_IFUNC definitions. */
-
-#include <stdlib.h>
-
-extern int foo1 (void);
-
-int
-main (void)
-{
- if (foo1 () != -1)
- abort ();
- return 0;
-}
diff --git a/elf/ifuncmain2pic.c b/elf/ifuncmain2pic.c
deleted file mode 100644
index 0006012a96..0000000000
--- a/elf/ifuncmain2pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmain2.c"
diff --git a/elf/ifuncmain2picstatic.c b/elf/ifuncmain2picstatic.c
deleted file mode 100644
index 3e89db536d..0000000000
--- a/elf/ifuncmain2picstatic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and -static. */
-
-#include "ifuncmain2.c"
diff --git a/elf/ifuncmain2static.c b/elf/ifuncmain2static.c
deleted file mode 100644
index 6932ae8066..0000000000
--- a/elf/ifuncmain2static.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -static. */
-
-#include "ifuncmain2.c"
diff --git a/elf/ifuncmain3.c b/elf/ifuncmain3.c
deleted file mode 100644
index 1574dd5cbe..0000000000
--- a/elf/ifuncmain3.c
+++ /dev/null
@@ -1,129 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with dlopen:
-
- 1. Direct function call.
- 2. Function pointer.
- 3. Visibility with override.
- */
-
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-typedef int (*foo_p) (void);
-
-int
-__attribute__ ((noinline))
-foo (void)
-{
- return -30;
-}
-
-int
-__attribute__ ((noinline))
-foo_hidden (void)
-{
- return -20;
-}
-
-int
-__attribute__ ((noinline))
-foo_protected (void)
-{
- return -40;
-}
-
-int
-main (void)
-{
- foo_p p;
- foo_p (*f) (void);
- int *ret;
-
- void *h = dlopen ("ifuncmod3.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot load: %s\n", dlerror ());
- return 1;
- }
-
- p = dlsym (h, "foo");
- if (p == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
- if ((*p) () != -1)
- abort ();
-
- f = dlsym (h, "get_foo_p");
- if (f == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- ret = dlsym (h, "ret_foo");
- if (ret == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- p = (*f) ();
- if (p != foo)
- abort ();
- if (foo () != -30)
- abort ();
- if (*ret != -30 || (*p) () != *ret)
- abort ();
-
- f = dlsym (h, "get_foo_hidden_p");
- if (f == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- ret = dlsym (h, "ret_foo_hidden");
- if (ret == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- p = (*f) ();
- if (foo_hidden () != -20)
- abort ();
- if (*ret != 1 || (*p) () != *ret)
- abort ();
-
- f = dlsym (h, "get_foo_protected_p");
- if (f == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- ret = dlsym (h, "ret_foo_protected");
- if (ret == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- p = (*f) ();
- if (p == foo_protected)
- abort ();
- if (foo_protected () != -40)
- abort ();
- if (*ret != 0 || (*p) () != *ret)
- abort ();
-
- if (dlclose (h) != 0)
- {
- printf ("cannot close: %s\n", dlerror ());
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/ifuncmain4.c b/elf/ifuncmain4.c
deleted file mode 100644
index e55fee2eb3..0000000000
--- a/elf/ifuncmain4.c
+++ /dev/null
@@ -1,4 +0,0 @@
-/* Test STT_GNU_IFUNC symbols in a single source file. */
-
-#include "ifuncmod1.c"
-#include "ifuncmain1.c"
diff --git a/elf/ifuncmain4picstatic.c b/elf/ifuncmain4picstatic.c
deleted file mode 100644
index 977d7f97fc..0000000000
--- a/elf/ifuncmain4picstatic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and -static. */
-
-#include "ifuncmain4.c"
diff --git a/elf/ifuncmain4static.c b/elf/ifuncmain4static.c
deleted file mode 100644
index c399977013..0000000000
--- a/elf/ifuncmain4static.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -static. */
-
-#include "ifuncmain4.c"
diff --git a/elf/ifuncmain5.c b/elf/ifuncmain5.c
deleted file mode 100644
index f398085cb4..0000000000
--- a/elf/ifuncmain5.c
+++ /dev/null
@@ -1,38 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with dynamic function pointer only. */
-
-#include <stdlib.h>
-
-extern int foo (void);
-extern int foo_protected (void);
-
-typedef int (*foo_p) (void);
-
-foo_p
-__attribute__ ((noinline))
-get_foo (void)
-{
- return foo;
-}
-
-foo_p
-__attribute__ ((noinline))
-get_foo_protected (void)
-{
- return foo_protected;
-}
-
-int
-main (void)
-{
- foo_p p;
-
- p = get_foo ();
- if ((*p) () != -1)
- abort ();
-
- p = get_foo_protected ();
- if ((*p) () != 0)
- abort ();
-
- return 0;
-}
diff --git a/elf/ifuncmain5pic.c b/elf/ifuncmain5pic.c
deleted file mode 100644
index e9144fbb20..0000000000
--- a/elf/ifuncmain5pic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC. */
-
-#include "ifuncmain5.c"
diff --git a/elf/ifuncmain5picstatic.c b/elf/ifuncmain5picstatic.c
deleted file mode 100644
index a0afe905d7..0000000000
--- a/elf/ifuncmain5picstatic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and -static. */
-
-#include "ifuncmain5.c"
diff --git a/elf/ifuncmain5pie.c b/elf/ifuncmain5pie.c
deleted file mode 100644
index 669f31eeda..0000000000
--- a/elf/ifuncmain5pie.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with PIE. */
-
-#include "ifuncmain5.c"
diff --git a/elf/ifuncmain5static.c b/elf/ifuncmain5static.c
deleted file mode 100644
index 72504404a5..0000000000
--- a/elf/ifuncmain5static.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -static. */
-
-#include "ifuncmain5.c"
diff --git a/elf/ifuncmain5staticpic.c b/elf/ifuncmain5staticpic.c
deleted file mode 100644
index 9e8bac254f..0000000000
--- a/elf/ifuncmain5staticpic.c
+++ /dev/null
@@ -1,3 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with -fPIC and no DSO. */
-
-#include "ifuncmain5.c"
diff --git a/elf/ifuncmain6pie.c b/elf/ifuncmain6pie.c
deleted file mode 100644
index 04faeb86ef..0000000000
--- a/elf/ifuncmain6pie.c
+++ /dev/null
@@ -1,65 +0,0 @@
-/* Test STT_GNU_IFUNC symbols in PIE:
-
- 1. Direct function call.
- 2. Function pointer.
- 3. Reference from a shared library.
- */
-
-#include <stdlib.h>
-#include "ifunc-sel.h"
-
-typedef int (*foo_p) (void);
-extern foo_p foo_ptr;
-
-static int
-one (void)
-{
- return -30;
-}
-
-void * foo_ifunc (void) __asm__ ("foo");
-__asm__(".type foo, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_ifunc (void)
-{
- return ifunc_one (one);
-}
-
-extern int foo (void);
-extern foo_p get_foo (void);
-extern foo_p get_foo_p (void);
-
-foo_p my_foo_ptr = foo;
-
-int
-main (void)
-{
- foo_p p;
-
- p = get_foo ();
- if (p != foo)
- abort ();
- if ((*p) () != -30)
- abort ();
-
- p = get_foo_p ();
- if (p != foo)
- abort ();
- if ((*p) () != -30)
- abort ();
-
- if (foo_ptr != foo)
- abort ();
- if (my_foo_ptr != foo)
- abort ();
- if ((*foo_ptr) () != -30)
- abort ();
- if ((*my_foo_ptr) () != -30)
- abort ();
- if (foo () != -30)
- abort ();
-
- return 0;
-}
diff --git a/elf/ifuncmain7.c b/elf/ifuncmain7.c
deleted file mode 100644
index 1e8f7ea38e..0000000000
--- a/elf/ifuncmain7.c
+++ /dev/null
@@ -1,72 +0,0 @@
-/* Test local STT_GNU_IFUNC symbols:
-
- 1. Direct function call.
- 2. Function pointer.
- */
-
-#include <stdlib.h>
-#include "ifunc-sel.h"
-
-extern int foo (void);
-
-static int
-one (void)
-{
- return -30;
-}
-
-static void * foo_ifunc (void) __asm__ ("foo");
-__asm__(".type foo, %gnu_indirect_function");
-
-static void *
-__attribute__ ((used))
-inhibit_stack_protector
-foo_ifunc (void)
-{
- return ifunc_one (one);
-}
-
-typedef int (*foo_p) (void);
-
-foo_p foo_ptr = foo;
-
-foo_p
-__attribute__ ((noinline))
-get_foo_p (void)
-{
- return foo_ptr;
-}
-
-foo_p
-__attribute__ ((noinline))
-get_foo (void)
-{
- return foo;
-}
-
-int
-main (void)
-{
- foo_p p;
-
- p = get_foo ();
- if (p != foo)
- abort ();
- if ((*p) () != -30)
- abort ();
-
- p = get_foo_p ();
- if (p != foo)
- abort ();
- if ((*p) () != -30)
- abort ();
-
- if (foo_ptr != foo)
- abort ();
- if ((*foo_ptr) () != -30)
- abort ();
- if (foo () != -30)
- abort ();
-
- return 0;
-}
diff --git a/elf/ifuncmain7pic.c b/elf/ifuncmain7pic.c
deleted file mode 100644
index fc37bf4469..0000000000
--- a/elf/ifuncmain7pic.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Test local STT_GNU_IFUNC symbols with -fPIC:
-
- 1. Direct function call.
- 2. Function pointer.
- */
-
-#include "ifuncmain7.c"
diff --git a/elf/ifuncmain7picstatic.c b/elf/ifuncmain7picstatic.c
deleted file mode 100644
index baf8934b95..0000000000
--- a/elf/ifuncmain7picstatic.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Test local STT_GNU_IFUNC symbols with -fPIC and -static:
-
- 1. Direct function call.
- 2. Function pointer.
- */
-
-#include "ifuncmain7.c"
diff --git a/elf/ifuncmain7pie.c b/elf/ifuncmain7pie.c
deleted file mode 100644
index 254d453f1e..0000000000
--- a/elf/ifuncmain7pie.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Test local STT_GNU_IFUNC symbols with PIE:
-
- 1. Direct function call.
- 2. Function pointer.
- */
-
-#include "ifuncmain7.c"
diff --git a/elf/ifuncmain7static.c b/elf/ifuncmain7static.c
deleted file mode 100644
index e470d570ef..0000000000
--- a/elf/ifuncmain7static.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Test local STT_GNU_IFUNC symbols with -static:
-
- 1. Direct function call.
- 2. Function pointer.
- */
-
-#include "ifuncmain7.c"
diff --git a/elf/ifuncmod1.c b/elf/ifuncmod1.c
deleted file mode 100644
index f0bf5fb45f..0000000000
--- a/elf/ifuncmod1.c
+++ /dev/null
@@ -1,100 +0,0 @@
-/* Test STT_GNU_IFUNC symbols:
-
- 1. Direct function call.
- 2. Function pointer.
- 3. Visibility.
- */
-#include "ifunc-sel.h"
-
-int global = -1;
-/* Can't use __attribute__((visibility("protected"))) until the GCC bug:
-
- https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65248
-
- is fixed. */
-asm (".protected global");
-
-static int
-one (void)
-{
- return 1;
-}
-
-static int
-minus_one (void)
-{
- return -1;
-}
-
-static int
-zero (void)
-{
- return 0;
-}
-
-void * foo_ifunc (void) __asm__ ("foo");
-__asm__(".type foo, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_ifunc (void)
-{
- return ifunc_sel (one, minus_one, zero);
-}
-
-void * foo_hidden_ifunc (void) __asm__ ("foo_hidden");
-__asm__(".type foo_hidden, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_hidden_ifunc (void)
-{
- return ifunc_sel (minus_one, one, zero);
-}
-
-void * foo_protected_ifunc (void) __asm__ ("foo_protected");
-__asm__(".type foo_protected, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_protected_ifunc (void)
-{
- return ifunc_sel (one, zero, minus_one);
-}
-
-/* Test hidden indirect function. */
-__asm__(".hidden foo_hidden");
-
-/* Test protected indirect function. */
-__asm__(".protected foo_protected");
-
-extern int foo (void);
-extern int foo_hidden (void);
-extern int foo_protected (void);
-extern int ret_foo;
-extern int ret_foo_hidden;
-extern int ret_foo_protected;
-
-#define FOO_P
-typedef int (*foo_p) (void);
-
-foo_p
-get_foo_p (void)
-{
- ret_foo = foo ();
- return foo;
-}
-
-foo_p
-get_foo_hidden_p (void)
-{
- ret_foo_hidden = foo_hidden ();
- return foo_hidden;
-}
-
-foo_p
-get_foo_protected_p (void)
-{
- ret_foo_protected = foo_protected ();
- return foo_protected;
-}
diff --git a/elf/ifuncmod3.c b/elf/ifuncmod3.c
deleted file mode 100644
index ca2d962600..0000000000
--- a/elf/ifuncmod3.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Test STT_GNU_IFUNC symbols with dlopen. */
-
-#include "ifuncmod1.c"
-
-int ret_foo;
-int ret_foo_hidden;
-int ret_foo_protected;
diff --git a/elf/ifuncmod5.c b/elf/ifuncmod5.c
deleted file mode 100644
index 5a957800e8..0000000000
--- a/elf/ifuncmod5.c
+++ /dev/null
@@ -1,64 +0,0 @@
-/* Test STT_GNU_IFUNC symbols without direct function call. */
-#include "ifunc-sel.h"
-
-int global = -1;
-/* Can't use __attribute__((visibility("protected"))) until the GCC bug:
-
- https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65248
-
- is fixed. */
-asm (".protected global");
-
-static int
-one (void)
-{
- return 1;
-}
-
-static int
-minus_one (void)
-{
- return -1;
-}
-
-static int
-zero (void)
-{
- return 0;
-}
-
-void * foo_ifunc (void) __asm__ ("foo");
-__asm__(".type foo, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_ifunc (void)
-{
- return ifunc_sel (one, minus_one, zero);
-}
-
-void * foo_hidden_ifunc (void) __asm__ ("foo_hidden");
-__asm__(".type foo_hidden, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_hidden_ifunc (void)
-{
- return ifunc_sel (minus_one, one, zero);
-}
-
-void * foo_protected_ifunc (void) __asm__ ("foo_protected");
-__asm__(".type foo_protected, %gnu_indirect_function");
-
-void *
-inhibit_stack_protector
-foo_protected_ifunc (void)
-{
- return ifunc_sel (one, zero, minus_one);
-}
-
-/* Test hidden indirect function. */
-__asm__(".hidden foo_hidden");
-
-/* Test protected indirect function. */
-__asm__(".protected foo_protected");
diff --git a/elf/ifuncmod6.c b/elf/ifuncmod6.c
deleted file mode 100644
index 2e16c1d06d..0000000000
--- a/elf/ifuncmod6.c
+++ /dev/null
@@ -1,19 +0,0 @@
-/* Test STT_GNU_IFUNC symbol reference in a shared library. */
-
-extern int foo (void);
-
-typedef int (*foo_p) (void);
-
-foo_p foo_ptr = foo;
-
-foo_p
-get_foo_p (void)
-{
- return foo_ptr;
-}
-
-foo_p
-get_foo (void)
-{
- return foo;
-}
diff --git a/elf/initfirst.c b/elf/initfirst.c
deleted file mode 100644
index 5ca83d21bc..0000000000
--- a/elf/initfirst.c
+++ /dev/null
@@ -1,22 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *h = dlopen ("firstobj.so", RTLD_LAZY);
- void *f;
- if (! h)
- {
- printf ("cannot find firstobj.so: %s\n", dlerror ());
- return 1;
- }
- f = dlsym (h, "foo");
- if (! f)
- {
- printf ("cannot find symbol foo: %s\n", dlerror ());
- return 2;
- }
- ((void (*) (void)) f) ();
- return 0;
-}
diff --git a/elf/interp.c b/elf/interp.c
deleted file mode 100644
index b6e8f04444..0000000000
--- a/elf/interp.c
+++ /dev/null
@@ -1,22 +0,0 @@
-/* interp - add information about dynamic loader to shared library objects.
- Copyright (C) 1996-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <runtime-linker.h>
-
-const char __invoke_dynamic_linker__[] __attribute__ ((section (".interp")))
- = RUNTIME_LINKER;
diff --git a/elf/lateglobal.c b/elf/lateglobal.c
deleted file mode 100644
index 4a1a7cd085..0000000000
--- a/elf/lateglobal.c
+++ /dev/null
@@ -1,47 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h[2];
- int fail;
- int (*fp) (void);
-
- mtrace ();
-
- h[0] = dlopen ("ltglobmod1.so", RTLD_LAZY);
- if (h[0] == NULL)
- {
- printf ("%s: cannot open %s: %s",
- __FUNCTION__, "ltglobmod1.so", dlerror ());
- exit (EXIT_FAILURE);
- }
- h[1] = dlopen ("ltglobmod2.so", RTLD_LAZY);
- if (h[1] == NULL)
- {
- printf ("%s: cannot open %s: %s",
- __FUNCTION__, "ltglobmod2.so", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- puts ("loaded \"ltglobmod1.so\" without RTLD_GLOBAL");
-
- fp = dlsym (h[1], "foo");
- if (fp == NULL)
- {
- printf ("cannot get address of `foo': %s", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- fail = fp ();
-
- puts ("back in main");
-
- dlclose (h[1]);
- dlclose (h[0]);
-
- return fail;
-}
diff --git a/elf/ldconfig.c b/elf/ldconfig.c
deleted file mode 100644
index 99caf9e9bb..0000000000
--- a/elf/ldconfig.c
+++ /dev/null
@@ -1,1418 +0,0 @@
-/* Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Andreas Jaeger <aj@suse.de>, 1999.
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published
- by the Free Software Foundation; version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, see <http://www.gnu.org/licenses/>. */
-
-#define PROCINFO_CLASS static
-#include <alloca.h>
-#include <argp.h>
-#include <dirent.h>
-#include <elf.h>
-#include <error.h>
-#include <errno.h>
-#include <inttypes.h>
-#include <libintl.h>
-#include <locale.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdio_ext.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdint.h>
-#include <sys/fcntl.h>
-#include <sys/mman.h>
-#include <sys/stat.h>
-#include <sys/types.h>
-#include <glob.h>
-#include <libgen.h>
-
-#include <ldconfig.h>
-#include <dl-cache.h>
-
-#include <dl-procinfo.h>
-
-#ifdef _DL_FIRST_PLATFORM
-# define _DL_FIRST_EXTRA (_DL_FIRST_PLATFORM + _DL_PLATFORMS_COUNT)
-#else
-# define _DL_FIRST_EXTRA _DL_HWCAP_COUNT
-#endif
-
-#ifndef LD_SO_CONF
-# define LD_SO_CONF SYSCONFDIR "/ld.so.conf"
-#endif
-
-/* Get libc version number. */
-#include <version.h>
-
-#define PACKAGE _libc_intl_domainname
-
-static const struct
-{
- const char *name;
- int flag;
-} lib_types[] =
-{
- {"libc4", FLAG_LIBC4},
- {"libc5", FLAG_ELF_LIBC5},
- {"libc6", FLAG_ELF_LIBC6},
- {"glibc2", FLAG_ELF_LIBC6}
-};
-
-
-/* List of directories to handle. */
-struct dir_entry
-{
- char *path;
- int flag;
- ino64_t ino;
- dev_t dev;
- struct dir_entry *next;
-};
-
-/* The list is unsorted, contains no duplicates. Entries are added at
- the end. */
-static struct dir_entry *dir_entries;
-
-/* Flags for different options. */
-/* Print Cache. */
-static int opt_print_cache;
-
-/* Be verbose. */
-int opt_verbose;
-
-/* Format to support. */
-/* 0: only libc5/glibc2; 1: both; 2: only glibc 2.2. */
-int opt_format = 1;
-
-/* Build cache. */
-static int opt_build_cache = 1;
-
-/* Enable symbolic link processing. If set, create or update symbolic
- links, and remove stale symbolic links. */
-static int opt_link = 1;
-
-/* Only process directories specified on the command line. */
-static int opt_only_cline;
-
-/* Path to root for chroot. */
-static char *opt_chroot;
-
-/* Manually link given shared libraries. */
-static int opt_manual_link;
-
-/* Should we ignore an old auxiliary cache file? */
-static int opt_ignore_aux_cache;
-
-/* Cache file to use. */
-static char *cache_file;
-
-/* Configuration file. */
-static const char *config_file;
-
-/* Mask to use for important hardware capabilities. */
-static unsigned long int hwcap_mask = HWCAP_IMPORTANT;
-
-/* Configuration-defined capabilities defined in kernel vDSOs. */
-static const char *hwcap_extra[64 - _DL_FIRST_EXTRA];
-
-/* Name and version of program. */
-static void print_version (FILE *stream, struct argp_state *state);
-void (*argp_program_version_hook) (FILE *, struct argp_state *)
- = print_version;
-
-/* Function to print some extra text in the help message. */
-static char *more_help (int key, const char *text, void *input);
-
-/* Definitions of arguments for argp functions. */
-static const struct argp_option options[] =
-{
- { "print-cache", 'p', NULL, 0, N_("Print cache"), 0},
- { "verbose", 'v', NULL, 0, N_("Generate verbose messages"), 0},
- { NULL, 'N', NULL, 0, N_("Don't build cache"), 0},
- { NULL, 'X', NULL, 0, N_("Don't update symbolic links"), 0},
- { NULL, 'r', N_("ROOT"), 0, N_("Change to and use ROOT as root directory"), 0},
- { NULL, 'C', N_("CACHE"), 0, N_("Use CACHE as cache file"), 0},
- { NULL, 'f', N_("CONF"), 0, N_("Use CONF as configuration file"), 0},
- { NULL, 'n', NULL, 0, N_("Only process directories specified on the command line. Don't build cache."), 0},
- { NULL, 'l', NULL, 0, N_("Manually link individual libraries."), 0},
- { "format", 'c', N_("FORMAT"), 0, N_("Format to use: new, old or compat (default)"), 0},
- { "ignore-aux-cache", 'i', NULL, 0, N_("Ignore auxiliary cache file"), 0},
- { NULL, 0, NULL, 0, NULL, 0 }
-};
-
-#define PROCINFO_CLASS static
-#include <dl-procinfo.c>
-
-/* Short description of program. */
-static const char doc[] = N_("Configure Dynamic Linker Run Time Bindings.");
-
-/* Prototype for option handler. */
-static error_t parse_opt (int key, char *arg, struct argp_state *state);
-
-/* Data structure to communicate with argp functions. */
-static struct argp argp =
-{
- options, parse_opt, NULL, doc, NULL, more_help, NULL
-};
-
-/* Check if string corresponds to an important hardware capability or
- a platform. */
-static int
-is_hwcap_platform (const char *name)
-{
- int hwcap_idx = _dl_string_hwcap (name);
-
- /* Is this a normal hwcap for the machine like "fpu?" */
- if (hwcap_idx != -1 && ((1 << hwcap_idx) & hwcap_mask))
- return 1;
-
- /* Is this a platform pseudo-hwcap like "i686?" */
- hwcap_idx = _dl_string_platform (name);
- if (hwcap_idx != -1)
- return 1;
-
- /* Is this one of the extra pseudo-hwcaps that we map beyond
- _DL_FIRST_EXTRA like "tls", or "nosegneg?" */
- for (hwcap_idx = _DL_FIRST_EXTRA; hwcap_idx < 64; ++hwcap_idx)
- if (hwcap_extra[hwcap_idx - _DL_FIRST_EXTRA] != NULL
- && !strcmp (name, hwcap_extra[hwcap_idx - _DL_FIRST_EXTRA]))
- return 1;
-
- return 0;
-}
-
-/* Get hwcap (including platform) encoding of path. */
-static uint64_t
-path_hwcap (const char *path)
-{
- char *str = xstrdup (path);
- char *ptr;
- uint64_t hwcap = 0;
- uint64_t h;
-
- size_t len;
-
- len = strlen (str);
- if (str[len] == '/')
- str[len] = '\0';
-
- /* Search pathname from the end and check for hwcap strings. */
- for (;;)
- {
- ptr = strrchr (str, '/');
-
- if (ptr == NULL)
- break;
-
- h = _dl_string_hwcap (ptr + 1);
-
- if (h == (uint64_t) -1)
- {
- h = _dl_string_platform (ptr + 1);
- if (h == (uint64_t) -1)
- {
- for (h = _DL_FIRST_EXTRA; h < 64; ++h)
- if (hwcap_extra[h - _DL_FIRST_EXTRA] != NULL
- && !strcmp (ptr + 1, hwcap_extra[h - _DL_FIRST_EXTRA]))
- break;
- if (h == 64)
- break;
- }
- }
- hwcap += 1ULL << h;
-
- /* Search the next part of the path. */
- *ptr = '\0';
- }
-
- free (str);
- return hwcap;
-}
-
-/* Handle program arguments. */
-static error_t
-parse_opt (int key, char *arg, struct argp_state *state)
-{
- switch (key)
- {
- case 'C':
- cache_file = arg;
- /* Ignore auxiliary cache since we use non-standard cache. */
- opt_ignore_aux_cache = 1;
- break;
- case 'f':
- config_file = arg;
- break;
- case 'i':
- opt_ignore_aux_cache = 1;
- break;
- case 'l':
- opt_manual_link = 1;
- break;
- case 'N':
- opt_build_cache = 0;
- break;
- case 'n':
- opt_build_cache = 0;
- opt_only_cline = 1;
- break;
- case 'p':
- opt_print_cache = 1;
- break;
- case 'r':
- opt_chroot = arg;
- break;
- case 'v':
- opt_verbose = 1;
- break;
- case 'X':
- opt_link = 0;
- break;
- case 'c':
- if (strcmp (arg, "old") == 0)
- opt_format = 0;
- else if (strcmp (arg, "compat") == 0)
- opt_format = 1;
- else if (strcmp (arg, "new") == 0)
- opt_format = 2;
- break;
- default:
- return ARGP_ERR_UNKNOWN;
- }
-
- return 0;
-}
-
-/* Print bug-reporting information in the help message. */
-static char *
-more_help (int key, const char *text, void *input)
-{
- char *tp = NULL;
- switch (key)
- {
- case ARGP_KEY_HELP_EXTRA:
- /* We print some extra information. */
- if (asprintf (&tp, gettext ("\
-For bug reporting instructions, please see:\n\
-%s.\n"), REPORT_BUGS_TO) < 0)
- return NULL;
- return tp;
- default:
- break;
- }
- return (char *) text;
-}
-
-/* Print the version information. */
-static void
-print_version (FILE *stream, struct argp_state *state)
-{
- fprintf (stream, "ldconfig %s%s\n", PKGVERSION, VERSION);
- fprintf (stream, gettext ("\
-Copyright (C) %s Free Software Foundation, Inc.\n\
-This is free software; see the source for copying conditions. There is NO\n\
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\
-"), "2017");
- fprintf (stream, gettext ("Written by %s.\n"),
- "Andreas Jaeger");
-}
-
-/* Add a single directory entry. */
-static void
-add_single_dir (struct dir_entry *entry, int verbose)
-{
- struct dir_entry *ptr, *prev;
-
- ptr = dir_entries;
- prev = ptr;
- while (ptr != NULL)
- {
- /* Check for duplicates. */
- if (ptr->ino == entry->ino && ptr->dev == entry->dev)
- {
- if (opt_verbose && verbose)
- error (0, 0, _("Path `%s' given more than once"), entry->path);
- /* Use the newer information. */
- ptr->flag = entry->flag;
- free (entry->path);
- free (entry);
- break;
- }
- prev = ptr;
- ptr = ptr->next;
- }
- /* Is this the first entry? */
- if (ptr == NULL && dir_entries == NULL)
- dir_entries = entry;
- else if (ptr == NULL)
- prev->next = entry;
-}
-
-/* Add one directory to the list of directories to process. */
-static void
-add_dir (const char *line)
-{
- unsigned int i;
- struct dir_entry *entry = xmalloc (sizeof (struct dir_entry));
- entry->next = NULL;
-
- /* Search for an '=' sign. */
- entry->path = xstrdup (line);
- char *equal_sign = strchr (entry->path, '=');
- if (equal_sign)
- {
- *equal_sign = '\0';
- ++equal_sign;
- entry->flag = FLAG_ANY;
- for (i = 0; i < sizeof (lib_types) / sizeof (lib_types[0]); ++i)
- if (strcmp (equal_sign, lib_types[i].name) == 0)
- {
- entry->flag = lib_types[i].flag;
- break;
- }
- if (entry->flag == FLAG_ANY)
- error (0, 0, _("%s is not a known library type"), equal_sign);
- }
- else
- {
- entry->flag = FLAG_ANY;
- }
-
- /* Canonify path: for now only remove leading and trailing
- whitespace and the trailing slashes. */
- i = strlen (entry->path);
-
- while (i > 0 && isspace (entry->path[i - 1]))
- entry->path[--i] = '\0';
-
- while (i > 0 && entry->path[i - 1] == '/')
- entry->path[--i] = '\0';
-
- if (i == 0)
- return;
-
- char *path = entry->path;
- if (opt_chroot)
- path = chroot_canon (opt_chroot, path);
-
- struct stat64 stat_buf;
- if (path == NULL || stat64 (path, &stat_buf))
- {
- if (opt_verbose)
- error (0, errno, _("Can't stat %s"), entry->path);
- free (entry->path);
- free (entry);
- }
- else
- {
- entry->ino = stat_buf.st_ino;
- entry->dev = stat_buf.st_dev;
-
- add_single_dir (entry, 1);
- }
-
- if (opt_chroot)
- free (path);
-}
-
-
-static int
-chroot_stat (const char *real_path, const char *path, struct stat64 *st)
-{
- int ret;
- char *canon_path;
-
- if (!opt_chroot)
- return stat64 (real_path, st);
-
- ret = lstat64 (real_path, st);
- if (ret || !S_ISLNK (st->st_mode))
- return ret;
-
- canon_path = chroot_canon (opt_chroot, path);
- if (canon_path == NULL)
- return -1;
-
- ret = stat64 (canon_path, st);
- free (canon_path);
- return ret;
-}
-
-/* Create a symbolic link from soname to libname in directory path. */
-static void
-create_links (const char *real_path, const char *path, const char *libname,
- const char *soname)
-{
- char *full_libname, *full_soname;
- char *real_full_libname, *real_full_soname;
- struct stat64 stat_lib, stat_so, lstat_so;
- int do_link = 1;
- int do_remove = 1;
- /* XXX: The logics in this function should be simplified. */
-
- /* Get complete path. */
- full_libname = alloca (strlen (path) + strlen (libname) + 2);
- full_soname = alloca (strlen (path) + strlen (soname) + 2);
- sprintf (full_libname, "%s/%s", path, libname);
- sprintf (full_soname, "%s/%s", path, soname);
- if (opt_chroot)
- {
- real_full_libname = alloca (strlen (real_path) + strlen (libname) + 2);
- real_full_soname = alloca (strlen (real_path) + strlen (soname) + 2);
- sprintf (real_full_libname, "%s/%s", real_path, libname);
- sprintf (real_full_soname, "%s/%s", real_path, soname);
- }
- else
- {
- real_full_libname = full_libname;
- real_full_soname = full_soname;
- }
-
- /* Does soname already exist and point to the right library? */
- if (chroot_stat (real_full_soname, full_soname, &stat_so) == 0)
- {
- if (chroot_stat (real_full_libname, full_libname, &stat_lib))
- {
- error (0, 0, _("Can't stat %s\n"), full_libname);
- return;
- }
- if (stat_lib.st_dev == stat_so.st_dev
- && stat_lib.st_ino == stat_so.st_ino)
- /* Link is already correct. */
- do_link = 0;
- else if (lstat64 (full_soname, &lstat_so) == 0
- && !S_ISLNK (lstat_so.st_mode))
- {
- error (0, 0, _("%s is not a symbolic link\n"), full_soname);
- do_link = 0;
- do_remove = 0;
- }
- }
- else if (lstat64 (real_full_soname, &lstat_so) != 0
- || !S_ISLNK (lstat_so.st_mode))
- /* Unless it is a stale symlink, there is no need to remove. */
- do_remove = 0;
-
- if (opt_verbose)
- printf ("\t%s -> %s", soname, libname);
-
- if (do_link && opt_link)
- {
- /* Remove old link. */
- if (do_remove)
- if (unlink (real_full_soname))
- {
- error (0, 0, _("Can't unlink %s"), full_soname);
- do_link = 0;
- }
- /* Create symbolic link. */
- if (do_link && symlink (libname, real_full_soname))
- {
- error (0, 0, _("Can't link %s to %s"), full_soname, libname);
- do_link = 0;
- }
- if (opt_verbose)
- {
- if (do_link)
- fputs (_(" (changed)\n"), stdout);
- else
- fputs (_(" (SKIPPED)\n"), stdout);
- }
- }
- else if (opt_verbose)
- fputs ("\n", stdout);
-}
-
-/* Manually link the given library. */
-static void
-manual_link (char *library)
-{
- char *path;
- char *real_path;
- char *real_library;
- char *libname;
- char *soname;
- struct stat64 stat_buf;
- int flag;
- unsigned int osversion;
-
- /* Prepare arguments for create_links call. Split library name in
- directory and filename first. Since path is allocated, we've got
- to be careful to free at the end. */
- path = xstrdup (library);
- libname = strrchr (path, '/');
-
- if (libname)
- {
- /* Successfully split names. Check if path is just "/" to avoid
- an empty path. */
- if (libname == path)
- {
- libname = library + 1;
- path = xrealloc (path, 2);
- strcpy (path, "/");
- }
- else
- {
- *libname = '\0';
- ++libname;
- }
- }
- else
- {
- /* There's no path, construct one. */
- libname = library;
- path = xrealloc (path, 2);
- strcpy (path, ".");
- }
-
- if (opt_chroot)
- {
- real_path = chroot_canon (opt_chroot, path);
- if (real_path == NULL)
- {
- error (0, errno, _("Can't find %s"), path);
- free (path);
- return;
- }
- real_library = alloca (strlen (real_path) + strlen (libname) + 2);
- sprintf (real_library, "%s/%s", real_path, libname);
- }
- else
- {
- real_path = path;
- real_library = library;
- }
-
- /* Do some sanity checks first. */
- if (lstat64 (real_library, &stat_buf))
- {
- error (0, errno, _("Cannot lstat %s"), library);
- free (path);
- return;
- }
- /* We don't want links here! */
- else if (!S_ISREG (stat_buf.st_mode))
- {
- error (0, 0, _("Ignored file %s since it is not a regular file."),
- library);
- free (path);
- return;
- }
-
- if (process_file (real_library, library, libname, &flag, &osversion,
- &soname, 0, &stat_buf))
- {
- error (0, 0, _("No link created since soname could not be found for %s"),
- library);
- free (path);
- return;
- }
- if (soname == NULL)
- soname = implicit_soname (libname, flag);
- create_links (real_path, path, libname, soname);
- free (soname);
- free (path);
-}
-
-
-/* Read a whole directory and search for libraries.
- The purpose is two-fold:
- - search for libraries which will be added to the cache
- - create symbolic links to the soname for each library
-
- This has to be done separatly for each directory.
-
- To keep track of which libraries to add to the cache and which
- links to create, we save a list of all libraries.
-
- The algorithm is basically:
- for all libraries in the directory do
- get soname of library
- if soname is already in list
- if new library is newer, replace entry
- otherwise ignore this library
- otherwise add library to list
-
- For example, if the two libraries libxy.so.1.1 and libxy.so.1.2
- exist and both have the same soname, e.g. libxy.so, a symbolic link
- is created from libxy.so.1.2 (the newer one) to libxy.so.
- libxy.so.1.2 and libxy.so are added to the cache - but not
- libxy.so.1.1. */
-
-/* Information for one library. */
-struct dlib_entry
-{
- char *name;
- char *soname;
- int flag;
- int is_link;
- unsigned int osversion;
- struct dlib_entry *next;
-};
-
-
-static void
-search_dir (const struct dir_entry *entry)
-{
- uint64_t hwcap = path_hwcap (entry->path);
- if (opt_verbose)
- {
- if (hwcap != 0)
- printf ("%s: (hwcap: %#.16" PRIx64 ")\n", entry->path, hwcap);
- else
- printf ("%s:\n", entry->path);
- }
-
- char *dir_name;
- char *real_file_name;
- size_t real_file_name_len;
- size_t file_name_len = PATH_MAX;
- char *file_name = alloca (file_name_len);
- if (opt_chroot)
- {
- dir_name = chroot_canon (opt_chroot, entry->path);
- real_file_name_len = PATH_MAX;
- real_file_name = alloca (real_file_name_len);
- }
- else
- {
- dir_name = entry->path;
- real_file_name_len = 0;
- real_file_name = file_name;
- }
-
- DIR *dir;
- if (dir_name == NULL || (dir = opendir (dir_name)) == NULL)
- {
- if (opt_verbose)
- error (0, errno, _("Can't open directory %s"), entry->path);
- if (opt_chroot && dir_name)
- free (dir_name);
- return;
- }
-
- struct dirent64 *direntry;
- struct dlib_entry *dlibs = NULL;
- while ((direntry = readdir64 (dir)) != NULL)
- {
- int flag;
-#ifdef _DIRENT_HAVE_D_TYPE
- /* We only look at links and regular files. */
- if (direntry->d_type != DT_UNKNOWN
- && direntry->d_type != DT_LNK
- && direntry->d_type != DT_REG
- && direntry->d_type != DT_DIR)
- continue;
-#endif /* _DIRENT_HAVE_D_TYPE */
- /* Does this file look like a shared library or is it a hwcap
- subdirectory? The dynamic linker is also considered as
- shared library. */
- if (((strncmp (direntry->d_name, "lib", 3) != 0
- && strncmp (direntry->d_name, "ld-", 3) != 0)
- || strstr (direntry->d_name, ".so") == NULL)
- && (
-#ifdef _DIRENT_HAVE_D_TYPE
- direntry->d_type == DT_REG ||
-#endif
- !is_hwcap_platform (direntry->d_name)))
- continue;
-
- size_t len = strlen (direntry->d_name);
- /* Skip temporary files created by the prelink program. Files with
- names like these are never really DSOs we want to look at. */
- if (len >= sizeof (".#prelink#") - 1)
- {
- if (strcmp (direntry->d_name + len - sizeof (".#prelink#") + 1,
- ".#prelink#") == 0)
- continue;
- if (len >= sizeof (".#prelink#.XXXXXX") - 1
- && memcmp (direntry->d_name + len - sizeof (".#prelink#.XXXXXX")
- + 1, ".#prelink#.", sizeof (".#prelink#.") - 1) == 0)
- continue;
- }
- len += strlen (entry->path) + 2;
- if (len > file_name_len)
- {
- file_name_len = len;
- file_name = alloca (file_name_len);
- if (!opt_chroot)
- real_file_name = file_name;
- }
- sprintf (file_name, "%s/%s", entry->path, direntry->d_name);
- if (opt_chroot)
- {
- len = strlen (dir_name) + strlen (direntry->d_name) + 2;
- if (len > real_file_name_len)
- {
- real_file_name_len = len;
- real_file_name = alloca (real_file_name_len);
- }
- sprintf (real_file_name, "%s/%s", dir_name, direntry->d_name);
- }
-
- struct stat64 lstat_buf;
-#ifdef _DIRENT_HAVE_D_TYPE
- /* We optimize and try to do the lstat call only if needed. */
- if (direntry->d_type != DT_UNKNOWN)
- lstat_buf.st_mode = DTTOIF (direntry->d_type);
- else
-#endif
- if (__glibc_unlikely (lstat64 (real_file_name, &lstat_buf)))
- {
- error (0, errno, _("Cannot lstat %s"), file_name);
- continue;
- }
-
- struct stat64 stat_buf;
- int is_dir;
- int is_link = S_ISLNK (lstat_buf.st_mode);
- if (is_link)
- {
- /* In case of symlink, we check if the symlink refers to
- a directory. */
- char *target_name = real_file_name;
- if (opt_chroot)
- {
- target_name = chroot_canon (opt_chroot, file_name);
- if (target_name == NULL)
- {
- if (strstr (file_name, ".so") == NULL)
- error (0, 0, _("Input file %s not found.\n"), file_name);
- continue;
- }
- }
- if (__glibc_unlikely (stat64 (target_name, &stat_buf)))
- {
- if (opt_verbose)
- error (0, errno, _("Cannot stat %s"), file_name);
-
- /* Remove stale symlinks. */
- if (opt_link && strstr (direntry->d_name, ".so."))
- unlink (real_file_name);
- continue;
- }
- is_dir = S_ISDIR (stat_buf.st_mode);
-
- /* lstat_buf is later stored, update contents. */
- lstat_buf.st_dev = stat_buf.st_dev;
- lstat_buf.st_ino = stat_buf.st_ino;
- lstat_buf.st_size = stat_buf.st_size;
- lstat_buf.st_ctime = stat_buf.st_ctime;
- }
- else
- is_dir = S_ISDIR (lstat_buf.st_mode);
-
- if (is_dir && is_hwcap_platform (direntry->d_name))
- {
- /* Handle subdirectory later. */
- struct dir_entry *new_entry;
-
- new_entry = xmalloc (sizeof (struct dir_entry));
- new_entry->path = xstrdup (file_name);
- new_entry->flag = entry->flag;
- new_entry->next = NULL;
-#ifdef _DIRENT_HAVE_D_TYPE
- /* We have filled in lstat only #ifndef
- _DIRENT_HAVE_D_TYPE. Fill it in if needed. */
- if (!is_link
- && direntry->d_type != DT_UNKNOWN
- && __builtin_expect (lstat64 (real_file_name, &lstat_buf), 0))
- {
- error (0, errno, _("Cannot lstat %s"), file_name);
- free (new_entry->path);
- free (new_entry);
- continue;
- }
-#endif
- new_entry->ino = lstat_buf.st_ino;
- new_entry->dev = lstat_buf.st_dev;
- add_single_dir (new_entry, 0);
- continue;
- }
- else if (!S_ISREG (lstat_buf.st_mode) && !is_link)
- continue;
-
- char *real_name;
- if (opt_chroot && is_link)
- {
- real_name = chroot_canon (opt_chroot, file_name);
- if (real_name == NULL)
- {
- if (strstr (file_name, ".so") == NULL)
- error (0, 0, _("Input file %s not found.\n"), file_name);
- continue;
- }
- }
- else
- real_name = real_file_name;
-
-#ifdef _DIRENT_HAVE_D_TYPE
- /* Call lstat64 if not done yet. */
- if (!is_link
- && direntry->d_type != DT_UNKNOWN
- && __builtin_expect (lstat64 (real_file_name, &lstat_buf), 0))
- {
- error (0, errno, _("Cannot lstat %s"), file_name);
- continue;
- }
-#endif
-
- /* First search whether the auxiliary cache contains this
- library already and it's not changed. */
- char *soname;
- unsigned int osversion;
- if (!search_aux_cache (&lstat_buf, &flag, &osversion, &soname))
- {
- if (process_file (real_name, file_name, direntry->d_name, &flag,
- &osversion, &soname, is_link, &lstat_buf))
- {
- if (real_name != real_file_name)
- free (real_name);
- continue;
- }
- else if (opt_build_cache)
- add_to_aux_cache (&lstat_buf, flag, osversion, soname);
- }
-
- if (soname == NULL)
- soname = implicit_soname (direntry->d_name, flag);
-
- /* A link may just point to itself. */
- if (is_link)
- {
- /* If the path the link points to isn't its soname or it is not
- the .so symlink for ld(1), we treat it as a normal file.
-
- You should always do this:
-
- libfoo.so -> SONAME -> Arbitrary package-chosen name.
-
- e.g. libfoo.so -> libfoo.so.1 -> libfooimp.so.9.99.
- Given a SONAME of libfoo.so.1.
-
- You should *never* do this:
-
- libfoo.so -> libfooimp.so.9.99
-
- If you do, and your SONAME is libfoo.so.1, then libfoo.so
- fails to point at the SONAME. In that case ldconfig may consider
- libfoo.so as another implementation of SONAME and will create
- symlinks against it causing problems when you try to upgrade
- or downgrade. The problems will arise because ldconfig will,
- depending on directory ordering, creat symlinks against libfoo.so
- e.g. libfoo.so.1.2 -> libfoo.so, but when libfoo.so is removed
- (typically by the removal of a development pacakge not required
- for the runtime) it will break the libfoo.so.1.2 symlink and the
- application will fail to start. */
- const char *real_base_name = basename (real_file_name);
-
- if (strcmp (real_base_name, soname) != 0)
- {
- len = strlen (real_base_name);
- if (len < strlen (".so")
- || strcmp (real_base_name + len - strlen (".so"), ".so") != 0
- || strncmp (real_base_name, soname, len) != 0)
- is_link = 0;
- }
- }
-
- if (real_name != real_file_name)
- free (real_name);
-
- if (is_link)
- {
- free (soname);
- soname = xstrdup (direntry->d_name);
- }
-
- if (flag == FLAG_ELF
- && (entry->flag == FLAG_ELF_LIBC5
- || entry->flag == FLAG_ELF_LIBC6))
- flag = entry->flag;
-
- /* Some sanity checks to print warnings. */
- if (opt_verbose)
- {
- if (flag == FLAG_ELF_LIBC5 && entry->flag != FLAG_ELF_LIBC5
- && entry->flag != FLAG_ANY)
- error (0, 0, _("libc5 library %s in wrong directory"), file_name);
- if (flag == FLAG_ELF_LIBC6 && entry->flag != FLAG_ELF_LIBC6
- && entry->flag != FLAG_ANY)
- error (0, 0, _("libc6 library %s in wrong directory"), file_name);
- if (flag == FLAG_LIBC4 && entry->flag != FLAG_LIBC4
- && entry->flag != FLAG_ANY)
- error (0, 0, _("libc4 library %s in wrong directory"), file_name);
- }
-
- /* Add library to list. */
- struct dlib_entry *dlib_ptr;
- for (dlib_ptr = dlibs; dlib_ptr != NULL; dlib_ptr = dlib_ptr->next)
- {
- /* Is soname already in list? */
- if (strcmp (dlib_ptr->soname, soname) == 0)
- {
- /* Prefer a file to a link, otherwise check which one
- is newer. */
- if ((!is_link && dlib_ptr->is_link)
- || (is_link == dlib_ptr->is_link
- && _dl_cache_libcmp (dlib_ptr->name, direntry->d_name) < 0))
- {
- /* It's newer - add it. */
- /* Flag should be the same - sanity check. */
- if (dlib_ptr->flag != flag)
- {
- if (dlib_ptr->flag == FLAG_ELF
- && (flag == FLAG_ELF_LIBC5 || flag == FLAG_ELF_LIBC6))
- dlib_ptr->flag = flag;
- else if ((dlib_ptr->flag == FLAG_ELF_LIBC5
- || dlib_ptr->flag == FLAG_ELF_LIBC6)
- && flag == FLAG_ELF)
- dlib_ptr->flag = flag;
- else
- error (0, 0, _("libraries %s and %s in directory %s have same soname but different type."),
- dlib_ptr->name, direntry->d_name,
- entry->path);
- }
- free (dlib_ptr->name);
- dlib_ptr->name = xstrdup (direntry->d_name);
- dlib_ptr->is_link = is_link;
- dlib_ptr->osversion = osversion;
- }
- /* Don't add this library, abort loop. */
- /* Also free soname, since it's dynamically allocated. */
- free (soname);
- break;
- }
- }
- /* Add the library if it's not already in. */
- if (dlib_ptr == NULL)
- {
- dlib_ptr = (struct dlib_entry *)xmalloc (sizeof (struct dlib_entry));
- dlib_ptr->name = xstrdup (direntry->d_name);
- dlib_ptr->soname = soname;
- dlib_ptr->flag = flag;
- dlib_ptr->is_link = is_link;
- dlib_ptr->osversion = osversion;
- /* Add at head of list. */
- dlib_ptr->next = dlibs;
- dlibs = dlib_ptr;
- }
- }
-
- closedir (dir);
-
- /* Now dlibs contains a list of all libs - add those to the cache
- and created all symbolic links. */
- struct dlib_entry *dlib_ptr;
- for (dlib_ptr = dlibs; dlib_ptr != NULL; dlib_ptr = dlib_ptr->next)
- {
- /* Don't create links to links. */
- if (dlib_ptr->is_link == 0)
- create_links (dir_name, entry->path, dlib_ptr->name,
- dlib_ptr->soname);
- if (opt_build_cache)
- add_to_cache (entry->path, dlib_ptr->soname, dlib_ptr->flag,
- dlib_ptr->osversion, hwcap);
- }
-
- /* Free all resources. */
- while (dlibs)
- {
- dlib_ptr = dlibs;
- free (dlib_ptr->soname);
- free (dlib_ptr->name);
- dlibs = dlibs->next;
- free (dlib_ptr);
- }
-
- if (opt_chroot && dir_name)
- free (dir_name);
-}
-
-/* Search through all libraries. */
-static void
-search_dirs (void)
-{
- struct dir_entry *entry;
-
- for (entry = dir_entries; entry != NULL; entry = entry->next)
- search_dir (entry);
-
- /* Free all allocated memory. */
- while (dir_entries)
- {
- entry = dir_entries;
- dir_entries = dir_entries->next;
- free (entry->path);
- free (entry);
- }
-}
-
-
-static void parse_conf_include (const char *config_file, unsigned int lineno,
- bool do_chroot, const char *pattern);
-
-/* Parse configuration file. */
-static void
-parse_conf (const char *filename, bool do_chroot)
-{
- FILE *file = NULL;
- char *line = NULL;
- const char *canon;
- size_t len = 0;
- unsigned int lineno;
-
- if (do_chroot && opt_chroot)
- {
- canon = chroot_canon (opt_chroot, filename);
- if (canon)
- file = fopen (canon, "r");
- else
- canon = filename;
- }
- else
- {
- canon = filename;
- file = fopen (filename, "r");
- }
-
- if (file == NULL)
- {
- error (0, errno, _("\
-Warning: ignoring configuration file that cannot be opened: %s"),
- canon);
- if (canon != filename)
- free ((char *) canon);
- return;
- }
-
- /* No threads use this stream. */
- __fsetlocking (file, FSETLOCKING_BYCALLER);
-
- if (canon != filename)
- free ((char *) canon);
-
- lineno = 0;
- do
- {
- ssize_t n = getline (&line, &len, file);
- if (n < 0)
- break;
-
- ++lineno;
- if (line[n - 1] == '\n')
- line[n - 1] = '\0';
-
- /* Because the file format does not know any form of quoting we
- can search forward for the next '#' character and if found
- make it terminating the line. */
- *strchrnul (line, '#') = '\0';
-
- /* Remove leading whitespace. NUL is no whitespace character. */
- char *cp = line;
- while (isspace (*cp))
- ++cp;
-
- /* If the line is blank it is ignored. */
- if (cp[0] == '\0')
- continue;
-
- if (!strncmp (cp, "include", 7) && isblank (cp[7]))
- {
- char *dir;
- cp += 8;
- while ((dir = strsep (&cp, " \t")) != NULL)
- if (dir[0] != '\0')
- parse_conf_include (filename, lineno, do_chroot, dir);
- }
- else if (!strncasecmp (cp, "hwcap", 5) && isblank (cp[5]))
- {
- cp += 6;
- char *p, *name = NULL;
- unsigned long int n = strtoul (cp, &cp, 0);
- if (cp != NULL && isblank (*cp))
- while ((p = strsep (&cp, " \t")) != NULL)
- if (p[0] != '\0')
- {
- if (name == NULL)
- name = p;
- else
- {
- name = NULL;
- break;
- }
- }
- if (name == NULL)
- {
- error (EXIT_FAILURE, 0, _("%s:%u: bad syntax in hwcap line"),
- filename, lineno);
- break;
- }
- if (n >= (64 - _DL_FIRST_EXTRA))
- error (EXIT_FAILURE, 0,
- _("%s:%u: hwcap index %lu above maximum %u"),
- filename, lineno, n, 64 - _DL_FIRST_EXTRA - 1);
- if (hwcap_extra[n] == NULL)
- {
- for (unsigned long int h = 0; h < (64 - _DL_FIRST_EXTRA); ++h)
- if (hwcap_extra[h] != NULL && !strcmp (name, hwcap_extra[h]))
- error (EXIT_FAILURE, 0,
- _("%s:%u: hwcap index %lu already defined as %s"),
- filename, lineno, h, name);
- hwcap_extra[n] = xstrdup (name);
- }
- else
- {
- if (strcmp (name, hwcap_extra[n]))
- error (EXIT_FAILURE, 0,
- _("%s:%u: hwcap index %lu already defined as %s"),
- filename, lineno, n, hwcap_extra[n]);
- if (opt_verbose)
- error (0, 0, _("%s:%u: duplicate hwcap %lu %s"),
- filename, lineno, n, name);
- }
- }
- else
- add_dir (cp);
- }
- while (!feof_unlocked (file));
-
- /* Free buffer and close file. */
- free (line);
- fclose (file);
-}
-
-/* Handle one word in an `include' line, a glob pattern of additional
- config files to read. */
-static void
-parse_conf_include (const char *config_file, unsigned int lineno,
- bool do_chroot, const char *pattern)
-{
- if (opt_chroot && pattern[0] != '/')
- error (EXIT_FAILURE, 0,
- _("need absolute file name for configuration file when using -r"));
-
- char *copy = NULL;
- if (pattern[0] != '/' && strchr (config_file, '/') != NULL)
- {
- if (asprintf (&copy, "%s/%s", dirname (strdupa (config_file)),
- pattern) < 0)
- error (EXIT_FAILURE, 0, _("memory exhausted"));
- pattern = copy;
- }
-
- glob64_t gl;
- int result;
- if (do_chroot && opt_chroot)
- {
- char *canon = chroot_canon (opt_chroot, pattern);
- if (canon == NULL)
- return;
- result = glob64 (canon, 0, NULL, &gl);
- free (canon);
- }
- else
- result = glob64 (pattern, 0, NULL, &gl);
-
- switch (result)
- {
- case 0:
- for (size_t i = 0; i < gl.gl_pathc; ++i)
- parse_conf (gl.gl_pathv[i], false);
- globfree64 (&gl);
- break;
-
- case GLOB_NOMATCH:
- break;
-
- case GLOB_NOSPACE:
- errno = ENOMEM;
- case GLOB_ABORTED:
- if (opt_verbose)
- error (0, errno, _("%s:%u: cannot read directory %s"),
- config_file, lineno, pattern);
- break;
-
- default:
- abort ();
- break;
- }
-
- free (copy);
-}
-
-/* Honour LD_HWCAP_MASK. */
-static void
-set_hwcap (void)
-{
- char *mask = getenv ("LD_HWCAP_MASK");
-
- if (mask)
- hwcap_mask = strtoul (mask, NULL, 0);
-}
-
-
-int
-main (int argc, char **argv)
-{
- /* Set locale via LC_ALL. */
- setlocale (LC_ALL, "");
-
- /* Set the text message domain. */
- textdomain (_libc_intl_domainname);
-
- /* Parse and process arguments. */
- int remaining;
- argp_parse (&argp, argc, argv, 0, &remaining, NULL);
-
- /* Remaining arguments are additional directories if opt_manual_link
- is not set. */
- if (remaining != argc && !opt_manual_link)
- {
- int i;
- for (i = remaining; i < argc; ++i)
- if (opt_build_cache && argv[i][0] != '/')
- error (EXIT_FAILURE, 0,
- _("relative path `%s' used to build cache"),
- argv[i]);
- else
- add_dir (argv[i]);
- }
-
- /* The last entry in hwcap_extra is reserved for the "tls" pseudo-hwcap which
- indicates support for TLS. This pseudo-hwcap is only used by old versions
- under which TLS support was optional. The entry is no longer needed, but
- must remain for compatibility. */
- hwcap_extra[63 - _DL_FIRST_EXTRA] = "tls";
-
- set_hwcap ();
-
- if (opt_chroot)
- {
- /* Normalize the path a bit, we might need it for printing later. */
- char *endp = rawmemchr (opt_chroot, '\0');
- while (endp > opt_chroot && endp[-1] == '/')
- --endp;
- *endp = '\0';
- if (endp == opt_chroot)
- opt_chroot = NULL;
-
- if (opt_chroot)
- {
- /* It is faster to use chroot if we can. */
- if (!chroot (opt_chroot))
- {
- if (chdir ("/"))
- error (EXIT_FAILURE, errno, _("Can't chdir to /"));
- opt_chroot = NULL;
- }
- }
- }
-
- if (cache_file == NULL)
- {
- cache_file = alloca (strlen (LD_SO_CACHE) + 1);
- strcpy (cache_file, LD_SO_CACHE);
- }
-
- if (config_file == NULL)
- config_file = LD_SO_CONF;
-
- if (opt_print_cache)
- {
- if (opt_chroot)
- {
- char *p = chroot_canon (opt_chroot, cache_file);
- if (p == NULL)
- error (EXIT_FAILURE, errno, _("Can't open cache file %s\n"),
- cache_file);
- cache_file = p;
- }
- print_cache (cache_file);
- if (opt_chroot)
- free (cache_file);
- exit (0);
- }
-
- if (opt_chroot)
- {
- /* Canonicalize the directory name of cache_file, not cache_file,
- because we'll rename a temporary cache file to it. */
- char *p = strrchr (cache_file, '/');
- char *canon = chroot_canon (opt_chroot,
- p ? (*p = '\0', cache_file) : "/");
-
- if (canon == NULL)
- error (EXIT_FAILURE, errno,
- _("Can't open cache file directory %s\n"),
- p ? cache_file : "/");
-
- if (p)
- ++p;
- else
- p = cache_file;
-
- cache_file = alloca (strlen (canon) + strlen (p) + 2);
- sprintf (cache_file, "%s/%s", canon, p);
- free (canon);
- }
-
- if (opt_manual_link)
- {
- /* Link all given libraries manually. */
- int i;
-
- for (i = remaining; i < argc; ++i)
- manual_link (argv[i]);
-
- exit (0);
- }
-
-
- if (opt_build_cache)
- init_cache ();
-
- if (!opt_only_cline)
- {
- parse_conf (config_file, true);
-
- /* Always add the standard search paths. */
- add_system_dir (SLIBDIR);
- if (strcmp (SLIBDIR, LIBDIR))
- add_system_dir (LIBDIR);
- }
-
- const char *aux_cache_file = _PATH_LDCONFIG_AUX_CACHE;
- if (opt_chroot)
- aux_cache_file = chroot_canon (opt_chroot, aux_cache_file);
-
- if (! opt_ignore_aux_cache && aux_cache_file)
- load_aux_cache (aux_cache_file);
- else
- init_aux_cache ();
-
- search_dirs ();
-
- if (opt_build_cache)
- {
- save_cache (cache_file);
- if (aux_cache_file)
- save_aux_cache (aux_cache_file);
- }
-
- return 0;
-}
diff --git a/elf/ldd.bash.in b/elf/ldd.bash.in
deleted file mode 100644
index 7dd1fccf24..0000000000
--- a/elf/ldd.bash.in
+++ /dev/null
@@ -1,203 +0,0 @@
-#! @BASH@
-# Copyright (C) 1996-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-
-# This is the `ldd' command, which lists what shared libraries are
-# used by given dynamically-linked executables. It works by invoking the
-# run-time dynamic linker as a command and setting the environment
-# variable LD_TRACE_LOADED_OBJECTS to a non-empty value.
-
-# We should be able to find the translation right at the beginning.
-TEXTDOMAIN=libc
-TEXTDOMAINDIR=@TEXTDOMAINDIR@
-
-RTLDLIST=@RTLD@
-warn=
-bind_now=
-verbose=
-
-while test $# -gt 0; do
- case "$1" in
- --vers | --versi | --versio | --version)
- echo 'ldd @PKGVERSION@@VERSION@'
- printf $"Copyright (C) %s Free Software Foundation, Inc.
-This is free software; see the source for copying conditions. There is NO
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
-" "2017"
- printf $"Written by %s and %s.
-" "Roland McGrath" "Ulrich Drepper"
- exit 0
- ;;
- --h | --he | --hel | --help)
- echo $"Usage: ldd [OPTION]... FILE...
- --help print this help and exit
- --version print version information and exit
- -d, --data-relocs process data relocations
- -r, --function-relocs process data and function relocations
- -u, --unused print unused direct dependencies
- -v, --verbose print all information
-"
- printf $"For bug reporting instructions, please see:\\n%s.\\n" \
- "@REPORT_BUGS_TO@"
- exit 0
- ;;
- -d | --d | --da | --dat | --data | --data- | --data-r | --data-re | \
- --data-rel | --data-relo | --data-reloc | --data-relocs)
- warn=yes
- shift
- ;;
- -r | --f | --fu | --fun | --func | --funct | --functi | --functio | \
- --function | --function- | --function-r | --function-re | --function-rel | \
- --function-relo | --function-reloc | --function-relocs)
- warn=yes
- bind_now=yes
- shift
- ;;
- -v | --verb | --verbo | --verbos | --verbose)
- verbose=yes
- shift
- ;;
- -u | --u | --un | --unu | --unus | --unuse | --unused)
- unused=yes
- shift
- ;;
- --v | --ve | --ver)
- echo >&2 $"ldd: option \`$1' is ambiguous"
- exit 1
- ;;
- --) # Stop option processing.
- shift; break
- ;;
- -*)
- echo >&2 'ldd:' $"unrecognized option" "\`$1'"
- echo >&2 $"Try \`ldd --help' for more information."
- exit 1
- ;;
- *)
- break
- ;;
- esac
-done
-
-nonelf ()
-{
- # Maybe extra code for non-ELF binaries.
- return 1;
-}
-
-add_env="LD_TRACE_LOADED_OBJECTS=1 LD_WARN=$warn LD_BIND_NOW=$bind_now"
-add_env="$add_env LD_VERBOSE=$verbose"
-if test "$unused" = yes; then
- add_env="$add_env LD_DEBUG=\"$LD_DEBUG${LD_DEBUG:+,}unused\""
-fi
-
-# The following command substitution is needed to make ldd work in SELinux
-# environments where the RTLD might not have permission to write to the
-# terminal. The extra "x" character prevents the shell from trimming trailing
-# newlines from command substitution results. This function is defined as a
-# subshell compound list (using "(...)") to prevent parameter assignments from
-# affecting the calling shell execution environment.
-try_trace() (
- output=$(eval $add_env '"$@"' 2>&1; rc=$?; printf 'x'; exit $rc)
- rc=$?
- printf '%s' "${output%x}"
- return $rc
-)
-
-case $# in
-0)
- echo >&2 'ldd:' $"missing file arguments"
- echo >&2 $"Try \`ldd --help' for more information."
- exit 1
- ;;
-1)
- single_file=t
- ;;
-*)
- single_file=f
- ;;
-esac
-
-result=0
-for file do
- # We don't list the file name when there is only one.
- test $single_file = t || echo "${file}:"
- case $file in
- */*) :
- ;;
- *) file=./$file
- ;;
- esac
- if test ! -e "$file"; then
- echo "ldd: ${file}:" $"No such file or directory" >&2
- result=1
- elif test ! -f "$file"; then
- echo "ldd: ${file}:" $"not regular file" >&2
- result=1
- elif test -r "$file"; then
- test -x "$file" || echo 'ldd:' $"\
-warning: you do not have execution permission for" "\`$file'" >&2
- RTLD=
- ret=1
- for rtld in ${RTLDLIST}; do
- if test -x $rtld; then
- verify_out=`${rtld} --verify "$file"`
- ret=$?
- case $ret in
- [02]) RTLD=${rtld}; break;;
- esac
- fi
- done
- case $ret in
- 0)
- # If the program exits with exit code 5, it means the process has been
- # invoked with __libc_enable_secure. Fall back to running it through
- # the dynamic linker.
- try_trace "$file"
- rc=$?
- if [ $rc = 5 ]; then
- try_trace "$RTLD" "$file"
- rc=$?
- fi
- [ $rc = 0 ] || result=1
- ;;
- 1)
- # This can be a non-ELF binary or no binary at all.
- nonelf "$file" || {
- echo $" not a dynamic executable"
- result=1
- }
- ;;
- 2)
- try_trace "$RTLD" "$file" || result=1
- ;;
- *)
- echo 'ldd:' ${RTLD} $"exited with unknown exit code" "($ret)" >&2
- exit 1
- ;;
- esac
- else
- echo 'ldd:' $"error: you do not have read permission for" "\`$file'" >&2
- result=1
- fi
-done
-
-exit $result
-# Local Variables:
-# mode:ksh
-# End:
diff --git a/elf/link.h b/elf/link.h
deleted file mode 100644
index 0e223ce9f0..0000000000
--- a/elf/link.h
+++ /dev/null
@@ -1,194 +0,0 @@
-/* Data structure for communication from the run-time dynamic linker for
- loaded ELF shared objects.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef _LINK_H
-#define _LINK_H 1
-
-#include <features.h>
-#include <elf.h>
-#include <dlfcn.h>
-#include <sys/types.h>
-
-/* We use this macro to refer to ELF types independent of the native wordsize.
- `ElfW(TYPE)' is used in place of `Elf32_TYPE' or `Elf64_TYPE'. */
-#define ElfW(type) _ElfW (Elf, __ELF_NATIVE_CLASS, type)
-#define _ElfW(e,w,t) _ElfW_1 (e, w, _##t)
-#define _ElfW_1(e,w,t) e##w##t
-
-#include <bits/elfclass.h> /* Defines __ELF_NATIVE_CLASS. */
-#include <bits/link.h>
-
-/* Rendezvous structure used by the run-time dynamic linker to communicate
- details of shared object loading to the debugger. If the executable's
- dynamic section has a DT_DEBUG element, the run-time linker sets that
- element's value to the address where this structure can be found. */
-
-struct r_debug
- {
- int r_version; /* Version number for this protocol. */
-
- struct link_map *r_map; /* Head of the chain of loaded objects. */
-
- /* This is the address of a function internal to the run-time linker,
- that will always be called when the linker begins to map in a
- library or unmap it, and again when the mapping change is complete.
- The debugger can set a breakpoint at this address if it wants to
- notice shared object mapping changes. */
- ElfW(Addr) r_brk;
- enum
- {
- /* This state value describes the mapping change taking place when
- the `r_brk' address is called. */
- RT_CONSISTENT, /* Mapping change is complete. */
- RT_ADD, /* Beginning to add a new object. */
- RT_DELETE /* Beginning to remove an object mapping. */
- } r_state;
-
- ElfW(Addr) r_ldbase; /* Base address the linker is loaded at. */
- };
-
-/* This is the instance of that structure used by the dynamic linker. */
-extern struct r_debug _r_debug;
-
-/* This symbol refers to the "dynamic structure" in the `.dynamic' section
- of whatever module refers to `_DYNAMIC'. So, to find its own
- `struct r_debug', a program could do:
- for (dyn = _DYNAMIC; dyn->d_tag != DT_NULL; ++dyn)
- if (dyn->d_tag == DT_DEBUG)
- r_debug = (struct r_debug *) dyn->d_un.d_ptr;
- */
-extern ElfW(Dyn) _DYNAMIC[];
-
-/* Structure describing a loaded shared object. The `l_next' and `l_prev'
- members form a chain of all the shared objects loaded at startup.
-
- These data structures exist in space used by the run-time dynamic linker;
- modifying them may have disastrous results. */
-
-struct link_map
- {
- /* These first few members are part of the protocol with the debugger.
- This is the same format used in SVR4. */
-
- ElfW(Addr) l_addr; /* Difference between the address in the ELF
- file and the addresses in memory. */
- char *l_name; /* Absolute file name object was found in. */
- ElfW(Dyn) *l_ld; /* Dynamic section of the shared object. */
- struct link_map *l_next, *l_prev; /* Chain of loaded objects. */
- };
-
-#ifdef __USE_GNU
-
-/* Version numbers for la_version handshake interface. */
-#define LAV_CURRENT 1
-
-/* Activity types signaled through la_activity. */
-enum
- {
- LA_ACT_CONSISTENT, /* Link map consistent again. */
- LA_ACT_ADD, /* New object will be added. */
- LA_ACT_DELETE /* Objects will be removed. */
- };
-
-/* Values representing origin of name for dynamic loading. */
-enum
- {
- LA_SER_ORIG = 0x01, /* Original name. */
- LA_SER_LIBPATH = 0x02, /* Directory from LD_LIBRARY_PATH. */
- LA_SER_RUNPATH = 0x04, /* Directory from RPATH/RUNPATH. */
- LA_SER_CONFIG = 0x08, /* Found through ldconfig. */
- LA_SER_DEFAULT = 0x40, /* Default directory. */
- LA_SER_SECURE = 0x80 /* Unused. */
- };
-
-/* Values for la_objopen return value. */
-enum
- {
- LA_FLG_BINDTO = 0x01, /* Audit symbols bound to this object. */
- LA_FLG_BINDFROM = 0x02 /* Audit symbols bound from this object. */
- };
-
-/* Values for la_symbind flags parameter. */
-enum
- {
- LA_SYMB_NOPLTENTER = 0x01, /* la_pltenter will not be called. */
- LA_SYMB_NOPLTEXIT = 0x02, /* la_pltexit will not be called. */
- LA_SYMB_STRUCTCALL = 0x04, /* Return value is a structure. */
- LA_SYMB_DLSYM = 0x08, /* Binding due to dlsym call. */
- LA_SYMB_ALTVALUE = 0x10 /* Value has been changed by a previous
- la_symbind call. */
- };
-
-struct dl_phdr_info
- {
- ElfW(Addr) dlpi_addr;
- const char *dlpi_name;
- const ElfW(Phdr) *dlpi_phdr;
- ElfW(Half) dlpi_phnum;
-
- /* Note: Following members were introduced after the first
- version of this structure was available. Check the SIZE
- argument passed to the dl_iterate_phdr callback to determine
- whether or not each later member is available. */
-
- /* Incremented when a new object may have been added. */
- __extension__ unsigned long long int dlpi_adds;
- /* Incremented when an object may have been removed. */
- __extension__ unsigned long long int dlpi_subs;
-
- /* If there is a PT_TLS segment, its module ID as used in
- TLS relocations, else zero. */
- size_t dlpi_tls_modid;
-
- /* The address of the calling thread's instance of this module's
- PT_TLS segment, if it has one and it has been allocated
- in the calling thread, otherwise a null pointer. */
- void *dlpi_tls_data;
- };
-
-__BEGIN_DECLS
-
-extern int dl_iterate_phdr (int (*__callback) (struct dl_phdr_info *,
- size_t, void *),
- void *__data);
-
-
-/* Prototypes for the ld.so auditing interfaces. These are not
- defined anywhere in ld.so but instead have to be provided by the
- auditing DSO. */
-extern unsigned int la_version (unsigned int __version);
-extern void la_activity (uintptr_t *__cookie, unsigned int __flag);
-extern char *la_objsearch (const char *__name, uintptr_t *__cookie,
- unsigned int __flag);
-extern unsigned int la_objopen (struct link_map *__map, Lmid_t __lmid,
- uintptr_t *__cookie);
-extern void la_preinit (uintptr_t *__cookie);
-extern uintptr_t la_symbind32 (Elf32_Sym *__sym, unsigned int __ndx,
- uintptr_t *__refcook, uintptr_t *__defcook,
- unsigned int *__flags, const char *__symname);
-extern uintptr_t la_symbind64 (Elf64_Sym *__sym, unsigned int __ndx,
- uintptr_t *__refcook, uintptr_t *__defcook,
- unsigned int *__flags, const char *__symname);
-extern unsigned int la_objclose (uintptr_t *__cookie);
-
-__END_DECLS
-
-#endif
-
-#endif /* link.h */
diff --git a/elf/loadfail.c b/elf/loadfail.c
deleted file mode 100644
index 7531aa958e..0000000000
--- a/elf/loadfail.c
+++ /dev/null
@@ -1,42 +0,0 @@
-#include <dlfcn.h>
-#include <error.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *su[5];
- void *h;
- int n;
-
- mtrace ();
-
- if ((su[0] = dlopen ("testobj1.so", RTLD_GLOBAL | RTLD_NOW)) == NULL
- || (su[1] = dlopen ("testobj2.so", RTLD_GLOBAL | RTLD_NOW)) == NULL
- || (su[2] = dlopen ("testobj3.so", RTLD_GLOBAL | RTLD_NOW)) == NULL
- || (su[3] = dlopen ("testobj4.so", RTLD_GLOBAL | RTLD_NOW)) == NULL
- || (su[4] = dlopen ("testobj5.so", RTLD_GLOBAL | RTLD_NOW)) == NULL)
- error (EXIT_FAILURE, 0, "failed to load shared object: %s", dlerror ());
-
- h = dlopen ("failobj.so", RTLD_GLOBAL | RTLD_NOW);
-
- printf ("h = %p, %s\n", h, h == NULL ? "ok" : "fail");
-
- for (n = 0; n < 5; ++n)
- if (dlclose (su[n]) != 0)
- {
- printf ("failed to unload su[%d]: %s\n", n, dlerror ());
- exit (EXIT_FAILURE);
- }
-
- return h != NULL;
-}
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return 10;
-}
diff --git a/elf/loadtest.c b/elf/loadtest.c
deleted file mode 100644
index 727469b496..0000000000
--- a/elf/loadtest.c
+++ /dev/null
@@ -1,202 +0,0 @@
-#include <assert.h>
-#include <dlfcn.h>
-#include <errno.h>
-#include <error.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-
-/* How many load/unload operations do we do. */
-#define TEST_ROUNDS 1000
-
-
-static struct
-{
- /* Name of the module. */
- const char *name;
- /* The handle. */
- void *handle;
-} testobjs[] =
-{
- { "testobj1.so", NULL },
- { "testobj2.so", NULL },
- { "testobj3.so", NULL },
- { "testobj4.so", NULL },
- { "testobj5.so", NULL },
- { "testobj6.so", NULL },
-};
-#define NOBJS (sizeof (testobjs) / sizeof (testobjs[0]))
-
-
-static const struct
-{
- /* Name of a function to call. */
- const char *fname;
- /* Index in status and handle array. */
- int index;
- /* Options while loading the module. */
- int options;
-} tests[] =
-{
- { "obj1func2", 0, RTLD_LAZY },
- { "obj1func1", 0, RTLD_LAZY | RTLD_GLOBAL },
- { "obj1func1", 0, RTLD_NOW, },
- { "obj1func2", 0, RTLD_NOW | RTLD_GLOBAL },
- { "obj2func2", 1, RTLD_LAZY },
- { "obj2func1", 1, RTLD_LAZY | RTLD_GLOBAL, },
- { "obj2func1", 1, RTLD_NOW, },
- { "obj2func2", 1, RTLD_NOW | RTLD_GLOBAL },
- { "obj3func2", 2, RTLD_LAZY },
- { "obj3func1", 2, RTLD_LAZY | RTLD_GLOBAL },
- { "obj3func1", 2, RTLD_NOW },
- { "obj3func2", 2, RTLD_NOW | RTLD_GLOBAL },
- { "obj4func2", 3, RTLD_LAZY },
- { "obj4func1", 3, RTLD_LAZY | RTLD_GLOBAL },
- { "obj4func1", 3, RTLD_NOW },
- { "obj4func2", 3, RTLD_NOW | RTLD_GLOBAL },
- { "obj5func2", 4, RTLD_LAZY },
- { "obj5func1", 4, RTLD_LAZY | RTLD_GLOBAL },
- { "obj5func1", 4, RTLD_NOW },
- { "obj5func2", 4, RTLD_NOW | RTLD_GLOBAL },
- { "obj6func2", 5, RTLD_LAZY },
- { "obj6func1", 5, RTLD_LAZY | RTLD_GLOBAL },
- { "obj6func1", 5, RTLD_NOW },
- { "obj6func2", 5, RTLD_NOW | RTLD_GLOBAL },
-};
-#define NTESTS (sizeof (tests) / sizeof (tests[0]))
-
-
-#include <include/link.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-#define OUT \
- for (map = MAPS; map != NULL; map = map->l_next) \
- if (map->l_type == lt_loaded) \
- printf ("name = \"%s\", direct_opencount = %d\n", \
- map->l_name, (int) map->l_direct_opencount); \
- fflush (stdout)
-
-
-int
-main (int argc, char *argv[])
-{
- int debug = argc > 1 && argv[1][0] != '\0';
- int count = TEST_ROUNDS;
- int result = 0;
- struct link_map *map;
-
- mtrace ();
-
- /* Just a seed. */
- srandom (TEST_ROUNDS);
-
- if (debug)
- {
- puts ("in the beginning");
- OUT;
- }
-
- while (count--)
- {
- int nr = random () % NTESTS;
- int index = tests[nr].index;
-
- printf ("%4d: %4d: ", count + 1, nr);
- fflush (stdout);
-
- if (testobjs[index].handle == NULL)
- {
- int (*fct) (int);
-
- /* Load the object. */
- testobjs[index].handle = dlopen (testobjs[index].name,
- tests[nr].options);
- if (testobjs[index].handle == NULL)
- error (EXIT_FAILURE, 0, "cannot load `%s': %s",
- testobjs[index].name, dlerror ());
-
- /* Test the function call. */
- fct = dlsym (testobjs[index].handle, tests[nr].fname);
- if (fct == NULL)
- error (EXIT_FAILURE, 0,
- "cannot get function `%s' from shared object `%s': %s",
- tests[nr].fname, testobjs[index].name, dlerror ());
-
- fct (10);
-
- printf ("successfully loaded `%s', handle %p\n",
- testobjs[index].name, testobjs[index].handle);
- }
- else
- {
- if (dlclose (testobjs[index].handle) != 0)
- {
- printf ("failed to close %s\n", testobjs[index].name);
- result = 1;
- }
- else
- printf ("successfully unloaded `%s', handle %p\n",
- testobjs[index].name, testobjs[index].handle);
-
- testobjs[index].handle = NULL;
-
- if (testobjs[0].handle == NULL
- && testobjs[1].handle == NULL
- && testobjs[5].handle == NULL)
- {
- /* In this case none of the objects above should be
- present. */
- for (map = MAPS; map != NULL; map = map->l_next)
- if (map->l_type == lt_loaded
- && (strstr (map->l_name, testobjs[0].name) != NULL
- || strstr (map->l_name, testobjs[1].name) != NULL
- || strstr (map->l_name, testobjs[5].name) != NULL))
- {
- printf ("`%s' is still loaded\n", map->l_name);
- result = 1;
- }
- }
- }
-
- if (debug)
- OUT;
- }
-
- /* Unload all loaded modules. */
- for (count = 0; count < (int) NOBJS; ++count)
- if (testobjs[count].handle != NULL)
- {
- printf ("\nclose: %s: l_initfini = %p, l_versions = %p\n",
- testobjs[count].name,
- ((struct link_map *) testobjs[count].handle)->l_initfini,
- ((struct link_map *) testobjs[count].handle)->l_versions);
-
- if (dlclose (testobjs[count].handle) != 0)
- {
- printf ("failed to close %s\n", testobjs[count].name);
- result = 1;
- }
- }
-
- /* Check whether all files are unloaded. */
- for (map = MAPS; map != NULL; map = map->l_next)
- if (map->l_type == lt_loaded)
- {
- printf ("name = \"%s\", direct_opencount = %d\n",
- map->l_name, (int) map->l_direct_opencount);
- result = 1;
- }
-
- return result;
-}
-
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return a - 1;
-}
diff --git a/elf/ltglobmod1.c b/elf/ltglobmod1.c
deleted file mode 100644
index 300fa9a89f..0000000000
--- a/elf/ltglobmod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int bar (void);
-
-int
-bar (void)
-{
- return 42;
-}
diff --git a/elf/ltglobmod2.c b/elf/ltglobmod2.c
deleted file mode 100644
index 33f14cc980..0000000000
--- a/elf/ltglobmod2.c
+++ /dev/null
@@ -1,33 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-extern int bar (void);
-extern int foo (void);
-
-int
-foo (void)
-{
- void *h;
- int res;
-
- /* Load ltglobalmod1 in the global namespace. */
- h = dlopen ("ltglobmod1.so", RTLD_GLOBAL | RTLD_LAZY);
- if (h == NULL)
- {
- printf ("%s: cannot open %s: %s",
- __FUNCTION__, "ltglobmod1.so", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- /* Call bar. This is undefined in the DSO. */
- puts ("about to call `bar'");
- fflush (stdout);
- res = bar ();
-
- printf ("bar returned %d\n", res);
-
- dlclose (h);
-
- return res != 42;
-}
diff --git a/elf/multiload.c b/elf/multiload.c
deleted file mode 100644
index e85cc96589..0000000000
--- a/elf/multiload.c
+++ /dev/null
@@ -1,105 +0,0 @@
-#include <dlfcn.h>
-#include <errno.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-
-int
-main (void)
-{
- void *a;
- void *b;
- void *c;
- void *d;
- char *wd;
- char *base;
- char *buf;
-
- mtrace ();
-
- /* Change to the binary directory. */
- if (chdir (OBJDIR) != 0)
- {
- printf ("cannot change to `%s': %m", OBJDIR);
- exit (EXIT_FAILURE);
- }
-
- wd = getcwd (NULL, 0);
- base = basename (wd);
- buf = alloca (strlen (wd) + strlen (base) + 5 + sizeof "testobj1.so");
-
- printf ("loading `%s'\n", "./testobj1.so");
- a = dlopen ("./testobj1.so", RTLD_NOW);
- if (a == NULL)
- {
- printf ("cannot load `./testobj1.so': %s\n", dlerror ());
- exit (EXIT_FAILURE);
- }
-
- stpcpy (stpcpy (stpcpy (buf, "../"), base), "/testobj1.so");
- printf ("loading `%s'\n", buf);
- b = dlopen (buf, RTLD_NOW);
- if (b == NULL)
- {
- printf ("cannot load `%s': %s\n", buf, dlerror ());
- exit (EXIT_FAILURE);
- }
-
- stpcpy (stpcpy (buf, wd), "/testobj1.so");
- printf ("loading `%s'\n", buf);
- c = dlopen (buf, RTLD_NOW);
- if (c == NULL)
- {
- printf ("cannot load `%s': %s\n", buf, dlerror ());
- exit (EXIT_FAILURE);
- }
-
- stpcpy (stpcpy (stpcpy (stpcpy (buf, wd), "/../"), base), "/testobj1.so");
- printf ("loading `%s'\n", buf);
- d = dlopen (buf, RTLD_NOW);
- if (d == NULL)
- {
- printf ("cannot load `%s': %s\n", buf, dlerror ());
- exit (EXIT_FAILURE);
- }
-
- if (a != b || b != c || c != d)
- {
- puts ("shared object loaded more than once");
- exit (EXIT_FAILURE);
- }
-
- if (dlclose (a) != 0)
- {
- puts ("closing `a' failed");
- exit (EXIT_FAILURE);
- }
- if (dlclose (b) != 0)
- {
- puts ("closing `a' failed");
- exit (EXIT_FAILURE);
- }
- if (dlclose (c) != 0)
- {
- puts ("closing `a' failed");
- exit (EXIT_FAILURE);
- }
- if (dlclose (d) != 0)
- {
- puts ("closing `a' failed");
- exit (EXIT_FAILURE);
- }
-
- free (wd);
-
- return 0;
-}
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return a;
-}
diff --git a/elf/neededobj1.c b/elf/neededobj1.c
deleted file mode 100644
index eb55adab39..0000000000
--- a/elf/neededobj1.c
+++ /dev/null
@@ -1,6 +0,0 @@
-extern void c_function (void);
-
-void
-c_function (void)
-{
-}
diff --git a/elf/neededobj2.c b/elf/neededobj2.c
deleted file mode 100644
index 5ad8a51d62..0000000000
--- a/elf/neededobj2.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern void b_function (void);
-extern void c_function (void);
-
-void
-b_function (void)
-{
- c_function();
-}
diff --git a/elf/neededobj3.c b/elf/neededobj3.c
deleted file mode 100644
index da25329aa7..0000000000
--- a/elf/neededobj3.c
+++ /dev/null
@@ -1,10 +0,0 @@
-extern void a_function (void);
-extern void b_function (void);
-extern void c_function (void);
-
-void
-a_function (void)
-{
- b_function ();
- c_function ();
-}
diff --git a/elf/neededobj4.c b/elf/neededobj4.c
deleted file mode 100644
index 3ea8540047..0000000000
--- a/elf/neededobj4.c
+++ /dev/null
@@ -1,12 +0,0 @@
-extern void a_function (void);
-extern void b_function (void);
-extern void c_function (void);
-extern void d_function (void);
-
-void
-d_function (void)
-{
- a_function ();
- b_function ();
- c_function ();
-}
diff --git a/elf/neededobj5.c b/elf/neededobj5.c
deleted file mode 100644
index 2d629b0880..0000000000
--- a/elf/neededobj5.c
+++ /dev/null
@@ -1,5 +0,0 @@
-extern void a1_function (void);
-
-void a1_function (void)
-{
-}
diff --git a/elf/neededobj6.c b/elf/neededobj6.c
deleted file mode 100644
index 639b6f195e..0000000000
--- a/elf/neededobj6.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern void a1_function (void);
-extern void a2_function (void);
-
-void a2_function (void)
-{
- a1_function ();
-}
diff --git a/elf/neededtest.c b/elf/neededtest.c
deleted file mode 100644
index 3cea499314..0000000000
--- a/elf/neededtest.c
+++ /dev/null
@@ -1,125 +0,0 @@
-#include <dlfcn.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-static int
-check_loaded_objects (const char **loaded)
-{
- struct link_map *lm;
- int n;
- int *found = NULL;
- int errors = 0;
-
- for (n = 0; loaded[n]; n++)
- /* NOTHING */;
-
- if (n)
- {
- found = (int *) alloca (sizeof (int) * n);
- memset (found, 0, sizeof (int) * n);
- }
-
- printf(" Name\n");
- printf(" --------------------------------------------------------\n");
- for (lm = MAPS; lm; lm = lm->l_next)
- {
- if (lm->l_name && lm->l_name[0])
- printf(" %s, count = %d\n", lm->l_name, (int) lm->l_direct_opencount);
- if (lm->l_type == lt_loaded && lm->l_name)
- {
- int match = 0;
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (strcmp (basename (loaded[n]), basename (lm->l_name)) == 0)
- {
- found[n] = 1;
- match = 1;
- break;
- }
- }
-
- if (match == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not unloaded\n", lm->l_name);
- }
- }
- }
-
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (found[n] == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not loaded\n", loaded[n]);
- }
- }
-
- return errors;
-}
-
-int
-main (void)
-{
- void *obj2[2];
- void *obj3;
- const char *loaded[] = { NULL, NULL, NULL, NULL };
- int errors = 0;
-
- printf ("\nThis is what is in memory now:\n");
- errors += check_loaded_objects (loaded);
-
- printf( "Loading shared object neededobj3.so\n");
- obj3 = dlopen( "neededobj3.so", RTLD_LAZY);
- if (obj3 == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[0] = "neededobj1.so";
- loaded[1] = "neededobj2.so";
- loaded[2] = "neededobj3.so";
- errors += check_loaded_objects (loaded);
-
- printf ("Now loading shared object neededobj2.so\n");
- obj2[0] = dlopen ("neededobj2.so", RTLD_LAZY);
- if (obj2[0] == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- errors += check_loaded_objects (loaded);
-
- printf ("And loading shared object neededobj2.so again\n");
- obj2[1] = dlopen ("neededobj2.so", RTLD_LAZY);
- if (obj2[1] == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj2.so for the first time\n");
- dlclose (obj2[0]);
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj3.so\n");
- dlclose (obj3);
- loaded[2] = NULL;
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj2.so for the second time\n");
- dlclose (obj2[1]);
- loaded[0] = NULL;
- loaded[1] = NULL;
- errors += check_loaded_objects (loaded);
-
- if (errors != 0)
- printf ("%d errors found\n", errors);
- return errors;
-}
diff --git a/elf/neededtest2.c b/elf/neededtest2.c
deleted file mode 100644
index 17c75f2ba3..0000000000
--- a/elf/neededtest2.c
+++ /dev/null
@@ -1,118 +0,0 @@
-#include <dlfcn.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-static int
-check_loaded_objects (const char **loaded)
-{
- struct link_map *lm;
- int n;
- int *found = NULL;
- int errors = 0;
-
- for (n = 0; loaded[n]; n++)
- /* NOTHING */;
-
- if (n)
- {
- found = (int *) alloca (sizeof (int) * n);
- memset (found, 0, sizeof (int) * n);
- }
-
- printf(" Name\n");
- printf(" --------------------------------------------------------\n");
- for (lm = MAPS; lm; lm = lm->l_next)
- {
- if (lm->l_name && lm->l_name[0])
- printf(" %s, count = %d\n", lm->l_name, (int) lm->l_direct_opencount);
- if (lm->l_type == lt_loaded && lm->l_name)
- {
- int match = 0;
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (strcmp (basename (loaded[n]), basename (lm->l_name)) == 0)
- {
- found[n] = 1;
- match = 1;
- break;
- }
- }
-
- if (match == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not unloaded\n", lm->l_name);
- }
- }
- }
-
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (found[n] == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not loaded\n", loaded[n]);
- }
- }
-
- return errors;
-}
-
-int
-main (void)
-{
- void *obj2;
- void *obj3[2];
- const char *loaded[] = { NULL, NULL, NULL, NULL };
- int errors = 0;
-
- printf ("\nThis is what is in memory now:\n");
- errors += check_loaded_objects (loaded);
- printf ("\nLoading shared object neededobj2.so\n");
- obj2 = dlopen ("neededobj2.so", RTLD_LAZY);
- if (obj2 == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[0] = "neededobj1.so";
- loaded[1] = "neededobj2.so";
- errors += check_loaded_objects (loaded);
- printf ("\nLoading shared object neededobj3.so\n");
- obj3[0] = dlopen( "neededobj3.so", RTLD_LAZY);
- if (obj3[0] == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[2] = "neededobj3.so";
- errors += check_loaded_objects (loaded);
- printf ("\nNow loading shared object neededobj3.so again\n");
- obj3[1] = dlopen ("neededobj3.so", RTLD_LAZY);
- if (obj3[1] == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- errors += check_loaded_objects (loaded);
- printf ("\nClosing neededobj3.so once\n");
- dlclose (obj3[0]);
- errors += check_loaded_objects (loaded);
- printf ("\nClosing neededobj2.so\n");
- dlclose (obj2);
- errors += check_loaded_objects (loaded);
- printf ("\nClosing neededobj3.so for the second time\n");
- dlclose (obj3[1]);
- loaded[0] = NULL;
- loaded[1] = NULL;
- loaded[2] = NULL;
- errors += check_loaded_objects (loaded);
- if (errors != 0)
- printf ("%d errors found\n", errors);
- return errors;
-}
diff --git a/elf/neededtest3.c b/elf/neededtest3.c
deleted file mode 100644
index 41970cf2c7..0000000000
--- a/elf/neededtest3.c
+++ /dev/null
@@ -1,129 +0,0 @@
-#include <dlfcn.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-static int
-check_loaded_objects (const char **loaded)
-{
- struct link_map *lm;
- int n;
- int *found = NULL;
- int errors = 0;
-
- for (n = 0; loaded[n]; n++)
- /* NOTHING */;
-
- if (n)
- {
- found = (int *) alloca (sizeof (int) * n);
- memset (found, 0, sizeof (int) * n);
- }
-
- printf(" Name\n");
- printf(" --------------------------------------------------------\n");
- for (lm = MAPS; lm; lm = lm->l_next)
- {
- if (lm->l_name && lm->l_name[0])
- printf(" %s, count = %d\n", lm->l_name, (int) lm->l_direct_opencount);
- if (lm->l_type == lt_loaded && lm->l_name)
- {
- int match = 0;
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (strcmp (basename (loaded[n]), basename (lm->l_name)) == 0)
- {
- found[n] = 1;
- match = 1;
- break;
- }
- }
-
- if (match == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not unloaded\n", lm->l_name);
- }
- }
- }
-
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (found[n] == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not loaded\n", loaded[n]);
- }
- }
-
- return errors;
-}
-
-int
-main (void)
-{
- void *obj2;
- void *obj3;
- void *obj4;
- const char *loaded[] = { NULL, NULL, NULL, NULL, NULL };
- int errors = 0;
-
- printf ("\nThis is what is in memory now:\n");
- errors += check_loaded_objects (loaded);
-
- printf ("Now loading shared object neededobj2.so\n");
- obj2 = dlopen ("neededobj2.so", RTLD_LAZY);
- if (obj2 == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[0] = "neededobj1.so";
- loaded[1] = "neededobj2.so";
- errors += check_loaded_objects (loaded);
-
- printf( "Loading shared object neededobj3.so\n");
- obj3 = dlopen( "neededobj3.so", RTLD_LAZY);
- if (obj3 == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[2] = "neededobj3.so";
- errors += check_loaded_objects (loaded);
-
-
- printf( "Loading shared object neededobj4.so\n");
- obj4 = dlopen( "neededobj4.so", RTLD_LAZY);
- if (obj4 == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- loaded[3] = "neededobj4.so";
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj2.so\n");
- dlclose (obj2);
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj3.so\n");
- dlclose (obj3);
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj4.so\n");
- dlclose (obj4);
- loaded[0] = NULL;
- loaded[1] = NULL;
- loaded[2] = NULL;
- loaded[3] = NULL;
- errors += check_loaded_objects (loaded);
-
- if (errors != 0)
- printf ("%d errors found\n", errors);
- return errors;
-}
diff --git a/elf/neededtest4.c b/elf/neededtest4.c
deleted file mode 100644
index 0ae0b7ff47..0000000000
--- a/elf/neededtest4.c
+++ /dev/null
@@ -1,158 +0,0 @@
-#include <dlfcn.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-static int
-check_loaded_objects (const char **loaded)
-{
- struct link_map *lm;
- int n;
- int *found = NULL;
- int errors = 0;
-
- for (n = 0; loaded[n]; n++)
- /* NOTHING */;
-
- if (n)
- {
- found = (int *) alloca (sizeof (int) * n);
- memset (found, 0, sizeof (int) * n);
- }
-
- printf(" Name\n");
- printf(" --------------------------------------------------------\n");
- for (lm = MAPS; lm; lm = lm->l_next)
- {
- if (lm->l_name && lm->l_name[0])
- printf(" %s, count = %d\n", lm->l_name, (int) lm->l_direct_opencount);
- if (lm->l_type == lt_loaded && lm->l_name)
- {
- int match = 0;
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (strcmp (basename (loaded[n]), basename (lm->l_name)) == 0)
- {
- found[n] = 1;
- match = 1;
- break;
- }
- }
-
- if (match == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not unloaded\n", lm->l_name);
- }
- }
- }
-
- for (n = 0; loaded[n] != NULL; n++)
- {
- if (found[n] == 0)
- {
- ++errors;
- printf ("ERRORS: %s is not loaded\n", loaded[n]);
- }
- }
-
- return errors;
-}
-
-extern void c_function (void);
-extern char *dirname (const char *__filename);
-
-int
-main (int argc, char **argv)
-{
- void *obj;
- const char *loaded[] = { NULL, NULL, NULL};
- int errors = 0;
- void (*f) (void);
- const char *dir = dirname (argv [0]);
- char *oldfilename;
- char *newfilename;
-
- c_function ();
-
- printf ("\nThis is what is in memory now:\n");
- errors += check_loaded_objects (loaded);
-
- printf( "Loading shared object neededobj6.so\n");
- obj = dlopen( "neededobj6.so", RTLD_LAZY);
- if (obj == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- f = dlsym (obj, "a2_function");
- if (f == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- f ();
- loaded[0] = "neededobj5.so";
- loaded[1] = "neededobj6.so";
- errors += check_loaded_objects (loaded);
-
- printf ("Closing neededobj6.so\n");
- dlclose (obj);
- loaded[0] = NULL;
- errors += check_loaded_objects (loaded);
-
- printf ("Rename neededobj5.so\n");
- oldfilename = alloca (strlen (dir) + 1 + sizeof ("neededobj5.so"));
- strcpy (oldfilename, dir);
- strcat (oldfilename, "/");
- strcat (oldfilename, "neededobj5.so");
- newfilename = alloca (strlen (oldfilename) + sizeof (".renamed"));
- strcpy (newfilename, oldfilename);
- strcat (newfilename, ".renamed");
- if (rename (oldfilename, newfilename))
- {
- perror ("rename");
- exit (1);
- }
-
- printf( "Loading shared object neededobj6.so\n");
- obj = dlopen( "neededobj6.so", RTLD_LAZY);
- if (obj == NULL)
- printf ("%s\n", dlerror ());
- else
- {
- printf ("neededobj6.so should fail to load\n");
- exit (1);
- }
-
- printf( "Loading shared object neededobj1.so\n");
- obj = dlopen( "neededobj1.so", RTLD_LAZY);
- if (obj == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- errors += check_loaded_objects (loaded);
- f = dlsym (obj, "c_function");
- if (f == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- f ();
-
- printf ("Restore neededobj5.so\n");
- if (rename (newfilename, oldfilename))
- {
- perror ("rename");
- exit (1);
- }
-
- if (errors != 0)
- printf ("%d errors found\n", errors);
- return errors;
-}
diff --git a/elf/next.c b/elf/next.c
deleted file mode 100644
index a0d532b8c3..0000000000
--- a/elf/next.c
+++ /dev/null
@@ -1,43 +0,0 @@
-#include <stdio.h>
-
-
-extern int successful_rtld_next_test (void);
-extern void *failing_rtld_next_use (void);
-
-
-static int
-do_test (void)
-{
- int result;
- void *addr;
-
- /* First try call a function which uses RTLD_NEXT and calls that
- function. */
- result = successful_rtld_next_test ();
- if (result == 42)
- {
- puts ("RTLD_NEXT seems to work for existing functions");
- result = 0;
- }
- else
- {
- printf ("Heh? `successful_rtld_next_test' returned %d\n", result);
- result = 1;
- }
-
- /* Next try a function which tries to get a function with RTLD_NEXT
- but that fails. This dlsym() call should return a NULL pointer
- and do nothing else. */
- addr = failing_rtld_next_use ();
- if (addr == NULL)
- puts ("dlsym returned NULL for non-existing function. Good");
- else
- {
- puts ("dlsym found something !?");
- result = 1;
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/nextmod1.c b/elf/nextmod1.c
deleted file mode 100644
index 56de3536a0..0000000000
--- a/elf/nextmod1.c
+++ /dev/null
@@ -1,30 +0,0 @@
-#include <dlfcn.h>
-
-extern int successful_rtld_next_test (void);
-extern void *failing_rtld_next_use (void);
-
-int nextmod1_dummy_var;
-
-int
-successful_rtld_next_test (void)
-{
- int (*fp) (void);
-
- /* Get the next function... */
- fp = (int (*) (void)) dlsym (RTLD_NEXT, __FUNCTION__);
-
- /* ...and simply call it. */
- return fp ();
-}
-
-
-void *
-failing_rtld_next_use (void)
-{
- void *ret = dlsym (RTLD_NEXT, __FUNCTION__);
-
- /* Ensure we are not tail call optimized, because then RTLD_NEXT
- might return this function. */
- ++nextmod1_dummy_var;
- return ret;
-}
diff --git a/elf/nextmod2.c b/elf/nextmod2.c
deleted file mode 100644
index b2c435f341..0000000000
--- a/elf/nextmod2.c
+++ /dev/null
@@ -1,10 +0,0 @@
-/* Very elaborated function. */
-
-extern int successful_rtld_next_test (void);
-
-
-int
-successful_rtld_next_test (void)
-{
- return 42;
-}
diff --git a/elf/nodel2mod1.c b/elf/nodel2mod1.c
deleted file mode 100644
index acddc4cf8b..0000000000
--- a/elf/nodel2mod1.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include <stdlib.h>
-void
-foo (void)
-{
- exit (0);
-}
-
-void
-__attribute__((destructor))
-bar (void)
-{
- static int i;
- foo ();
- ++i;
-}
-void
-baz (void)
-{
-}
diff --git a/elf/nodel2mod2.c b/elf/nodel2mod2.c
deleted file mode 100644
index d0020240a8..0000000000
--- a/elf/nodel2mod2.c
+++ /dev/null
@@ -1,7 +0,0 @@
-void
-__attribute__((constructor))
-xxx (void)
-{
- extern void baz (void);
- baz ();
-}
diff --git a/elf/nodel2mod3.c b/elf/nodel2mod3.c
deleted file mode 100644
index 6d1a0d47b7..0000000000
--- a/elf/nodel2mod3.c
+++ /dev/null
@@ -1 +0,0 @@
-int x;
diff --git a/elf/nodelete.c b/elf/nodelete.c
deleted file mode 100644
index c8d71152f2..0000000000
--- a/elf/nodelete.c
+++ /dev/null
@@ -1,210 +0,0 @@
-#include <dlfcn.h>
-#include <setjmp.h>
-#include <signal.h>
-#include <stdio.h>
-
-
-static sigjmp_buf jmpbuf;
-
-
-int fini_ran;
-
-
-static void
-__attribute__ ((noreturn))
-handler (int sig)
-{
- siglongjmp (jmpbuf, 1);
-}
-
-
-static int
-do_test (void)
-{
- /* We are testing the two possibilities to mark an object as not deletable:
- - marked on the linker commandline with `-z nodelete'
- - with the RTLD_NODELETE flag at dlopen()-time.
-
- The test we are performing should be safe. We are loading the objects,
- get the address of variables in the respective object, unload the object
- and then try to read the variable. If the object is unloaded this
- should lead to an segmentation fault. */
- int result = 0;
- void *p;
- struct sigaction sa;
-
- sa.sa_handler = handler;
- sigfillset (&sa.sa_mask);
- sa.sa_flags = SA_RESTART;
-
- if (sigaction (SIGSEGV, &sa, NULL) == -1)
- printf ("cannot install signal handler: %m\n");
-
- p = dlopen ("nodelmod1.so", RTLD_LAZY);
- if (p == NULL)
- {
- printf ("failed to load \"nodelmod1.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- {
- int *varp;
-
- puts ("succeeded loading \"nodelmod1.so\"");
-
- varp = dlsym (p, "var1");
- if (varp == NULL)
- {
- puts ("failed to get address of \"var1\" in \"nodelmod1.so\"");
- result = 1;
- }
- else
- {
- *varp = 20000720;
-
- /* Now close the object. */
- fini_ran = 0;
- if (dlclose (p) != 0)
- {
- puts ("failed to close \"nodelmod1.so\"");
- result = 1;
- }
- else if (! sigsetjmp (jmpbuf, 1))
- {
- /* Access the variable again. */
- if (*varp != 20000720)
- {
- puts ("\"var1\" value not correct");
- result = 1;
- }
- else if (fini_ran != 0)
- {
- puts ("destructor of \"nodelmod1.so\" ran");
- result = 1;
- }
- else
- puts ("-z nodelete test succeeded");
- }
- else
- {
- /* We caught an segmentation fault. */
- puts ("\"nodelmod1.so\" got deleted");
- result = 1;
- }
- }
- }
-
- p = dlopen ("nodelmod2.so", RTLD_LAZY | RTLD_NODELETE);
- if (p == NULL)
- {
- printf ("failed to load \"nodelmod2.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- {
- int *varp;
-
- puts ("succeeded loading \"nodelmod2.so\"");
-
- varp = dlsym (p, "var2");
- if (varp == NULL)
- {
- puts ("failed to get address of \"var2\" in \"nodelmod2.so\"");
- result = 1;
- }
- else
- {
- *varp = 42;
-
- /* Now close the object. */
- fini_ran = 0;
- if (dlclose (p) != 0)
- {
- puts ("failed to close \"nodelmod2.so\"");
- result = 1;
- }
- else if (! sigsetjmp (jmpbuf, 1))
- {
- /* Access the variable again. */
- if (*varp != 42)
- {
- puts ("\"var2\" value not correct");
- result = 1;
- }
- else if (fini_ran != 0)
- {
- puts ("destructor of \"nodelmod2.so\" ran");
- result = 1;
- }
- else
- puts ("RTLD_NODELETE test succeeded");
- }
- else
- {
- /* We caught an segmentation fault. */
- puts ("\"nodelmod2.so\" got deleted");
- result = 1;
- }
- }
- }
-
- p = dlopen ("nodelmod3.so", RTLD_LAZY);
- if (p == NULL)
- {
- printf ("failed to load \"nodelmod3.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- {
- int *(*fctp) (void);
-
- puts ("succeeded loading \"nodelmod3.so\"");
-
- fctp = dlsym (p, "addr");
- if (fctp == NULL)
- {
- puts ("failed to get address of \"addr\" in \"nodelmod3.so\"");
- result = 1;
- }
- else
- {
- int *varp = fctp ();
-
- *varp = -1;
-
- /* Now close the object. */
- fini_ran = 0;
- if (dlclose (p) != 0)
- {
- puts ("failed to close \"nodelmod3.so\"");
- result = 1;
- }
- else if (! sigsetjmp (jmpbuf, 1))
- {
- /* Access the variable again. */
- if (*varp != -1)
- {
- puts ("\"var_in_mod4\" value not correct");
- result = 1;
- }
- else if (fini_ran != 0)
- {
- puts ("destructor of \"nodelmod4.so\" ran");
- result = 1;
- }
- else
- puts ("-z nodelete in dependency succeeded");
- }
- else
- {
- /* We caught an segmentation fault. */
- puts ("\"nodelmod4.so\" got deleted");
- result = 1;
- }
- }
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/nodelete2.c b/elf/nodelete2.c
deleted file mode 100644
index b3d7e31a08..0000000000
--- a/elf/nodelete2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-#include <stdlib.h>
-#include <dlfcn.h>
-
-int
-main (void)
-{
- void *handle = dlopen ("nodel2mod3.so", RTLD_LAZY);
- if (handle == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- dlclose (handle);
- exit (1);
-}
diff --git a/elf/nodelmod1.c b/elf/nodelmod1.c
deleted file mode 100644
index fc24a7b172..0000000000
--- a/elf/nodelmod1.c
+++ /dev/null
@@ -1,9 +0,0 @@
-int var1 = 42;
-
-static void
-__attribute__ ((__destructor__))
-destr (void)
-{
- extern int fini_ran;
- fini_ran = 1;
-}
diff --git a/elf/nodelmod2.c b/elf/nodelmod2.c
deleted file mode 100644
index 6bd7108a13..0000000000
--- a/elf/nodelmod2.c
+++ /dev/null
@@ -1,9 +0,0 @@
-int var2 = 100;
-
-static void
-__attribute__ ((__destructor__))
-destr (void)
-{
- extern int fini_ran;
- fini_ran = 1;
-}
diff --git a/elf/nodelmod3.c b/elf/nodelmod3.c
deleted file mode 100644
index 817c94db6e..0000000000
--- a/elf/nodelmod3.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int var_in_mod4;
-extern int *addr (void);
-
-int *
-addr (void)
-{
- return &var_in_mod4;
-}
diff --git a/elf/nodelmod4.c b/elf/nodelmod4.c
deleted file mode 100644
index 2cca43a6e8..0000000000
--- a/elf/nodelmod4.c
+++ /dev/null
@@ -1,9 +0,0 @@
-int var_in_mod4 = 99;
-
-static void
-__attribute__ ((__destructor__))
-destr (void)
-{
- extern int fini_ran;
- fini_ran = 1;
-}
diff --git a/elf/nodlopen.c b/elf/nodlopen.c
deleted file mode 100644
index 642bdb3011..0000000000
--- a/elf/nodlopen.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- if (dlopen ("nodlopenmod.so", RTLD_LAZY) != NULL)
- {
- puts ("opening \"nodlopenmod.so\" succeeded, FAIL");
- return 1;
- }
-
- puts ("opening \"nodlopenmod.so\" failed, OK");
- return 0;
-}
diff --git a/elf/nodlopen2.c b/elf/nodlopen2.c
deleted file mode 100644
index a223f36834..0000000000
--- a/elf/nodlopen2.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- if (dlopen ("nodlopenmod2.so", RTLD_LAZY) != NULL)
- {
- puts ("opening \"nodlopenmod2.so\" succeeded, FAIL");
- return 1;
- }
-
- puts ("opening \"nodlopenmod2.so\" failed, OK");
- return 0;
-}
diff --git a/elf/nodlopenmod.c b/elf/nodlopenmod.c
deleted file mode 100644
index 4bcf8c9786..0000000000
--- a/elf/nodlopenmod.c
+++ /dev/null
@@ -1 +0,0 @@
-int a = 42;
diff --git a/elf/nodlopenmod2.c b/elf/nodlopenmod2.c
deleted file mode 100644
index e72ae53e95..0000000000
--- a/elf/nodlopenmod2.c
+++ /dev/null
@@ -1,9 +0,0 @@
-extern int a;
-
-extern int foo (void);
-
-int
-foo (void)
-{
- return a;
-}
diff --git a/elf/noload.c b/elf/noload.c
deleted file mode 100644
index bcc85efc27..0000000000
--- a/elf/noload.c
+++ /dev/null
@@ -1,81 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <mcheck.h>
-
-int
-main (void)
-{
- int result = 0;
- void *p;
-
- mtrace ();
-
- /* First try to load an object which is a dependency. This should
- succeed. */
- p = dlopen ("testobj1.so", RTLD_LAZY | RTLD_NOLOAD);
- if (p == NULL)
- {
- printf ("cannot open \"testobj1.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- {
- puts ("loading \"testobj1.so\" succeeded, OK");
- dlclose (p);
- }
-
- /* Now try loading an object which is not already loaded. */
- if (dlopen ("testobj5.so", RTLD_LAZY | RTLD_NOLOAD) != NULL)
- {
- puts ("succeeded in loading \"testobj5.so\"");
- result = 1;
- }
- else
- {
- /* Load the object and run the same test again. */
- puts ("\"testobj5.so\" wasn't loaded and RTLD_NOLOAD prevented it, OK");
-
- p = dlopen ("testobj5.so", RTLD_LAZY);
-
- if (p == NULL)
- {
- printf ("cannot open \"testobj5.so\" without RTLD_NOLOAD: %s\n",
- dlerror ());
- result = 1;
- }
- else
- {
- puts ("loading \"testobj5.so\" succeeded, OK");
-
- void *q = dlopen ("testobj5.so", RTLD_LAZY | RTLD_NOLOAD);
- if (q == NULL)
- {
- printf ("cannot open \"testobj5.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- {
- puts ("loading \"testobj5.so\" with RTLD_NOLOAD succeeded, OK");
- dlclose (q);
- }
-
- if (dlclose (p) != 0)
- {
- printf ("cannot close \"testobj5.so\": %s\n", dlerror ());
- result = 1;
- }
- else
- puts ("closing \"testobj5.so\" succeeded, OK");
- }
- }
-
- return result;
-}
-
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return 42 + a;
-}
diff --git a/elf/order.c b/elf/order.c
deleted file mode 100644
index ca617cbc09..0000000000
--- a/elf/order.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <unistd.h>
-
-void init (void) __attribute__ ((constructor));
-void
-__attribute__ ((constructor))
-init (void)
-{
- write (1, "4", 1);
-}
-
-void fini (void) __attribute__ ((destructor));
-void
-__attribute__ ((destructor))
-fini (void)
-{
- write (1, "5", 1);
-}
-
-extern int dep1 (void);
-
-int
-main (void)
-{
- return dep1 () != 42;
-}
diff --git a/elf/order2.c b/elf/order2.c
deleted file mode 100644
index bcf266d5b1..0000000000
--- a/elf/order2.c
+++ /dev/null
@@ -1,45 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-
-int call_puts;
-
-static int
-do_test (void)
-{
- call_puts = 1;
-
- void *h1 = dlopen ("$ORIGIN/order2mod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- puts ("cannot load order2mod1");
- return 1;
- }
- void *h2 = dlopen ("$ORIGIN/order2mod2.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("cannot load order2mod2");
- return 1;
- }
- if (dlclose (h1) != 0)
- {
- puts ("dlclose order2mod1 failed");
- return 1;
- }
- if (dlclose (h2) != 0)
- {
- puts ("dlclose order2mod2 failed");
- return 1;
- }
- return 0;
-}
-
-#include <support/test-driver.c>
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- if (call_puts)
- puts ("5");
-}
diff --git a/elf/order2mod1.c b/elf/order2mod1.c
deleted file mode 100644
index b695db29b7..0000000000
--- a/elf/order2mod1.c
+++ /dev/null
@@ -1,8 +0,0 @@
-#include <stdio.h>
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- putchar ('1');
-}
diff --git a/elf/order2mod2.c b/elf/order2mod2.c
deleted file mode 100644
index 026cd2acc4..0000000000
--- a/elf/order2mod2.c
+++ /dev/null
@@ -1,18 +0,0 @@
-#include <stdio.h>
-
-extern int foo (void);
-extern int bar (void);
-
-void
-__attribute__ ((constructor))
-init (void)
-{
- (void) (foo () - bar ());
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- putchar ('2');
-}
diff --git a/elf/order2mod3.c b/elf/order2mod3.c
deleted file mode 100644
index 7913a79925..0000000000
--- a/elf/order2mod3.c
+++ /dev/null
@@ -1,14 +0,0 @@
-#include <stdio.h>
-
-int
-bar (void)
-{
- return 1;
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- putchar ('4');
-}
diff --git a/elf/order2mod4.c b/elf/order2mod4.c
deleted file mode 100644
index 4f2026f041..0000000000
--- a/elf/order2mod4.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern int bar (void);
-
-int
-foo (void)
-{
- return 42 + bar ();
-}
-
-static void
-__attribute__ ((destructor))
-fini (void)
-{
- putchar ('3');
-}
diff --git a/elf/origtest.c b/elf/origtest.c
deleted file mode 100644
index 1cacabcc39..0000000000
--- a/elf/origtest.c
+++ /dev/null
@@ -1,39 +0,0 @@
-#include <dlfcn.h>
-#include <error.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h;
- int (*fp) (int);
- int res;
-
- h = dlopen ("${ORIGIN}/testobj1.so", RTLD_LAZY);
- if (h == NULL)
- error (EXIT_FAILURE, 0, "while loading `%s': %s", "testobj1.so",
- dlerror ());
-
- fp = dlsym (h, "obj1func1");
- if (fp == NULL)
- error (EXIT_FAILURE, 0, "getting `obj1func1' in `%s': %s",
- "testobj1.so", dlerror ());
-
- res = fp (10);
- printf ("fp(10) = %d\n", res);
-
- if (dlclose (h) != 0)
- error (EXIT_FAILURE, 0, "while close `%s': %s",
- "testobj1.so", dlerror ());
-
- return res != 42;
-}
-
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return a + 10;
-}
diff --git a/elf/pathoptobj.c b/elf/pathoptobj.c
deleted file mode 100644
index a452c2d7d4..0000000000
--- a/elf/pathoptobj.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int in_renamed (int);
-
-
-int
-in_renamed (int a)
-{
- return a - 10;
-}
diff --git a/elf/pldd-xx.c b/elf/pldd-xx.c
deleted file mode 100644
index 5ce0bce4c9..0000000000
--- a/elf/pldd-xx.c
+++ /dev/null
@@ -1,251 +0,0 @@
-/* Copyright (C) 2011-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@gmail.com>, 2011.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#define E(name) E_(name, CLASS)
-#define E_(name, cl) E__(name, cl)
-#define E__(name, cl) name##cl
-#define EW(type) EW_(Elf, CLASS, type)
-#define EW_(e, w, t) EW__(e, w, _##t)
-#define EW__(e, w, t) e##w##t
-
-#define pldd_assert(name, exp) \
- typedef int __assert_##name[((exp) != 0) - 1]
-
-
-struct E(link_map)
-{
- EW(Addr) l_addr;
- EW(Addr) l_name;
- EW(Addr) l_ld;
- EW(Addr) l_next;
- EW(Addr) l_prev;
- EW(Addr) l_real;
- Lmid_t l_ns;
- EW(Addr) l_libname;
-};
-#if CLASS == __ELF_NATIVE_CLASS
-pldd_assert (l_addr, (offsetof (struct link_map, l_addr)
- == offsetof (struct E(link_map), l_addr)));
-pldd_assert (l_name, (offsetof (struct link_map, l_name)
- == offsetof (struct E(link_map), l_name)));
-pldd_assert (l_next, (offsetof (struct link_map, l_next)
- == offsetof (struct E(link_map), l_next)));
-#endif
-
-
-struct E(libname_list)
-{
- EW(Addr) name;
- EW(Addr) next;
-};
-#if CLASS == __ELF_NATIVE_CLASS
-pldd_assert (name, (offsetof (struct libname_list, name)
- == offsetof (struct E(libname_list), name)));
-pldd_assert (next, (offsetof (struct libname_list, next)
- == offsetof (struct E(libname_list), next)));
-#endif
-
-struct E(r_debug)
-{
- int r_version;
-#if CLASS == 64
- int pad;
-#endif
- EW(Addr) r_map;
-};
-#if CLASS == __ELF_NATIVE_CLASS
-pldd_assert (r_version, (offsetof (struct r_debug, r_version)
- == offsetof (struct E(r_debug), r_version)));
-pldd_assert (r_map, (offsetof (struct r_debug, r_map)
- == offsetof (struct E(r_debug), r_map)));
-#endif
-
-
-static int
-
-E(find_maps) (pid_t pid, void *auxv, size_t auxv_size)
-{
- EW(Addr) phdr = 0;
- unsigned int phnum = 0;
- unsigned int phent = 0;
-
- EW(auxv_t) *auxvXX = (EW(auxv_t) *) auxv;
- for (int i = 0; i < auxv_size / sizeof (EW(auxv_t)); ++i)
- switch (auxvXX[i].a_type)
- {
- case AT_PHDR:
- phdr = auxvXX[i].a_un.a_val;
- break;
- case AT_PHNUM:
- phnum = auxvXX[i].a_un.a_val;
- break;
- case AT_PHENT:
- phent = auxvXX[i].a_un.a_val;
- break;
- default:
- break;
- }
-
- if (phdr == 0 || phnum == 0 || phent == 0)
- error (EXIT_FAILURE, 0, gettext ("cannot find program header of process"));
-
- EW(Phdr) *p = alloca (phnum * phent);
- if (pread64 (memfd, p, phnum * phent, phdr) != phnum * phent)
- {
- error (0, 0, gettext ("cannot read program header"));
- return EXIT_FAILURE;
- }
-
- /* Determine the load offset. We need this for interpreting the
- other program header entries so we do this in a separate loop.
- Fortunately it is the first time unless someone does something
- stupid when linking the application. */
- EW(Addr) offset = 0;
- for (unsigned int i = 0; i < phnum; ++i)
- if (p[i].p_type == PT_PHDR)
- {
- offset = phdr - p[i].p_vaddr;
- break;
- }
-
- EW(Addr) list = 0;
- char *interp = NULL;
- for (unsigned int i = 0; i < phnum; ++i)
- if (p[i].p_type == PT_DYNAMIC)
- {
- EW(Dyn) *dyn = xmalloc (p[i].p_filesz);
- if (pread64 (memfd, dyn, p[i].p_filesz, offset + p[i].p_vaddr)
- != p[i].p_filesz)
- {
- error (0, 0, gettext ("cannot read dynamic section"));
- return EXIT_FAILURE;
- }
-
- /* Search for the DT_DEBUG entry. */
- for (unsigned int j = 0; j < p[i].p_filesz / sizeof (EW(Dyn)); ++j)
- if (dyn[j].d_tag == DT_DEBUG && dyn[j].d_un.d_ptr != 0)
- {
- struct E(r_debug) r;
- if (pread64 (memfd, &r, sizeof (r), dyn[j].d_un.d_ptr)
- != sizeof (r))
- {
- error (0, 0, gettext ("cannot read r_debug"));
- return EXIT_FAILURE;
- }
-
- if (r.r_map != 0)
- {
- list = r.r_map;
- break;
- }
- }
-
- free (dyn);
- break;
- }
- else if (p[i].p_type == PT_INTERP)
- {
- interp = alloca (p[i].p_filesz);
- if (pread64 (memfd, interp, p[i].p_filesz, offset + p[i].p_vaddr)
- != p[i].p_filesz)
- {
- error (0, 0, gettext ("cannot read program interpreter"));
- return EXIT_FAILURE;
- }
- }
-
- if (list == 0)
- {
- if (interp == NULL)
- {
- // XXX check whether the executable itself is the loader
- return EXIT_FAILURE;
- }
-
- // XXX perhaps try finding ld.so and _r_debug in it
-
- return EXIT_FAILURE;
- }
-
- /* Print the PID and program name first. */
- printf ("%lu:\t%s\n", (unsigned long int) pid, exe);
-
- /* Iterate over the list of objects and print the information. */
- struct scratch_buffer tmpbuf;
- scratch_buffer_init (&tmpbuf);
- int status = 0;
- do
- {
- struct E(link_map) m;
- if (pread64 (memfd, &m, sizeof (m), list) != sizeof (m))
- {
- error (0, 0, gettext ("cannot read link map"));
- status = EXIT_FAILURE;
- goto out;
- }
-
- EW(Addr) name_offset = m.l_name;
- again:
- while (1)
- {
- ssize_t n = pread64 (memfd, tmpbuf.data, tmpbuf.length, name_offset);
- if (n == -1)
- {
- error (0, 0, gettext ("cannot read object name"));
- status = EXIT_FAILURE;
- goto out;
- }
-
- if (memchr (tmpbuf.data, '\0', n) != NULL)
- break;
-
- if (!scratch_buffer_grow (&tmpbuf))
- {
- error (0, 0, gettext ("cannot allocate buffer for object name"));
- status = EXIT_FAILURE;
- goto out;
- }
- }
-
- if (((char *)tmpbuf.data)[0] == '\0' && name_offset == m.l_name
- && m.l_libname != 0)
- {
- /* Try the l_libname element. */
- struct E(libname_list) ln;
- if (pread64 (memfd, &ln, sizeof (ln), m.l_libname) == sizeof (ln))
- {
- name_offset = ln.name;
- goto again;
- }
- }
-
- /* Skip over the executable. */
- if (((char *)tmpbuf.data)[0] != '\0')
- printf ("%s\n", (char *)tmpbuf.data);
-
- list = m.l_next;
- }
- while (list != 0);
-
- out:
- scratch_buffer_free (&tmpbuf);
- return status;
-}
-
-
-#undef CLASS
diff --git a/elf/pldd.c b/elf/pldd.c
deleted file mode 100644
index ddfa88d63b..0000000000
--- a/elf/pldd.c
+++ /dev/null
@@ -1,344 +0,0 @@
-/* List dynamic shared objects linked into given process.
- Copyright (C) 2011-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@gmail.com>, 2011.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <alloca.h>
-#include <argp.h>
-#include <assert.h>
-#include <dirent.h>
-#include <elf.h>
-#include <errno.h>
-#include <error.h>
-#include <fcntl.h>
-#include <libintl.h>
-#include <link.h>
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/ptrace.h>
-#include <sys/stat.h>
-#include <sys/wait.h>
-#include <scratch_buffer.h>
-
-#include <ldsodefs.h>
-#include <version.h>
-
-/* Global variables. */
-extern char *program_invocation_short_name;
-#define PACKAGE _libc_intl_domainname
-
-/* External functions. */
-#include <programs/xmalloc.h>
-
-/* Name and version of program. */
-static void print_version (FILE *stream, struct argp_state *state);
-void (*argp_program_version_hook) (FILE *, struct argp_state *) = print_version;
-
-/* Function to print some extra text in the help message. */
-static char *more_help (int key, const char *text, void *input);
-
-/* Definitions of arguments for argp functions. */
-static const struct argp_option options[] =
-{
- { NULL, 0, NULL, 0, NULL }
-};
-
-/* Short description of program. */
-static const char doc[] = N_("\
-List dynamic shared objects loaded into process.");
-
-/* Strings for arguments in help texts. */
-static const char args_doc[] = N_("PID");
-
-/* Prototype for option handler. */
-static error_t parse_opt (int key, char *arg, struct argp_state *state);
-
-/* Data structure to communicate with argp functions. */
-static struct argp argp =
-{
- options, parse_opt, args_doc, doc, NULL, more_help, NULL
-};
-
-// File descriptor of /proc/*/mem file.
-static int memfd;
-
-/* Name of the executable */
-static char *exe;
-
-/* Local functions. */
-static int get_process_info (int dfd, long int pid);
-static void wait_for_ptrace_stop (long int pid);
-
-
-int
-main (int argc, char *argv[])
-{
- /* Parse and process arguments. */
- int remaining;
- argp_parse (&argp, argc, argv, 0, &remaining, NULL);
-
- if (remaining != argc - 1)
- {
- fprintf (stderr,
- gettext ("Exactly one parameter with process ID required.\n"));
- argp_help (&argp, stderr, ARGP_HELP_SEE, program_invocation_short_name);
- return 1;
- }
-
- assert (sizeof (pid_t) == sizeof (int)
- || sizeof (pid_t) == sizeof (long int));
- char *endp;
- errno = 0;
- long int pid = strtol (argv[remaining], &endp, 10);
- if (pid < 0 || (pid == ULONG_MAX && errno == ERANGE) || *endp != '\0'
- || (sizeof (pid_t) < sizeof (pid) && pid > INT_MAX))
- error (EXIT_FAILURE, 0, gettext ("invalid process ID '%s'"),
- argv[remaining]);
-
- /* Determine the program name. */
- char buf[7 + 3 * sizeof (pid)];
- snprintf (buf, sizeof (buf), "/proc/%lu", pid);
- int dfd = open (buf, O_RDONLY | O_DIRECTORY);
- if (dfd == -1)
- error (EXIT_FAILURE, errno, gettext ("cannot open %s"), buf);
-
- struct scratch_buffer exebuf;
- scratch_buffer_init (&exebuf);
- ssize_t nexe;
- while ((nexe = readlinkat (dfd, "exe",
- exebuf.data, exebuf.length)) == exebuf.length)
- {
- if (!scratch_buffer_grow (&exebuf))
- {
- nexe = -1;
- break;
- }
- }
- if (nexe == -1)
- exe = (char *) "<program name undetermined>";
- else
- {
- exe = exebuf.data;
- exe[nexe] = '\0';
- }
-
- /* Stop all threads since otherwise the list of loaded modules might
- change while we are reading it. */
- struct thread_list
- {
- pid_t tid;
- struct thread_list *next;
- } *thread_list = NULL;
-
- int taskfd = openat (dfd, "task", O_RDONLY | O_DIRECTORY | O_CLOEXEC);
- if (taskfd == 1)
- error (EXIT_FAILURE, errno, gettext ("cannot open %s/task"), buf);
- DIR *dir = fdopendir (taskfd);
- if (dir == NULL)
- error (EXIT_FAILURE, errno, gettext ("cannot prepare reading %s/task"),
- buf);
-
- struct dirent64 *d;
- while ((d = readdir64 (dir)) != NULL)
- {
- if (! isdigit (d->d_name[0]))
- continue;
-
- errno = 0;
- long int tid = strtol (d->d_name, &endp, 10);
- if (tid < 0 || (tid == ULONG_MAX && errno == ERANGE) || *endp != '\0'
- || (sizeof (pid_t) < sizeof (pid) && tid > INT_MAX))
- error (EXIT_FAILURE, 0, gettext ("invalid thread ID '%s'"),
- d->d_name);
-
- if (ptrace (PTRACE_ATTACH, tid, NULL, NULL) != 0)
- {
- /* There might be a race between reading the directory and
- threads terminating. Ignore errors attaching to unknown
- threads unless this is the main thread. */
- if (errno == ESRCH && tid != pid)
- continue;
-
- error (EXIT_FAILURE, errno, gettext ("cannot attach to process %lu"),
- tid);
- }
-
- wait_for_ptrace_stop (tid);
-
- struct thread_list *newp = alloca (sizeof (*newp));
- newp->tid = tid;
- newp->next = thread_list;
- thread_list = newp;
- }
-
- closedir (dir);
-
- int status = get_process_info (dfd, pid);
-
- assert (thread_list != NULL);
- do
- {
- ptrace (PTRACE_DETACH, thread_list->tid, NULL, NULL);
- thread_list = thread_list->next;
- }
- while (thread_list != NULL);
-
- close (dfd);
-
- return status;
-}
-
-
-/* Wait for PID to enter ptrace-stop state after being attached. */
-static void
-wait_for_ptrace_stop (long int pid)
-{
- int status;
-
- /* While waiting for SIGSTOP being delivered to the tracee we have to
- reinject any other pending signal. Ignore all other errors. */
- while (waitpid (pid, &status, __WALL) == pid && WIFSTOPPED (status))
- {
- /* The STOP signal should not be delivered to the tracee. */
- if (WSTOPSIG (status) == SIGSTOP)
- return;
- if (ptrace (PTRACE_CONT, pid, NULL,
- (void *) (uintptr_t) WSTOPSIG (status)))
- /* The only possible error is that the process died. */
- return;
- }
-}
-
-
-/* Handle program arguments. */
-static error_t
-parse_opt (int key, char *arg, struct argp_state *state)
-{
- switch (key)
- {
- default:
- return ARGP_ERR_UNKNOWN;
- }
- return 0;
-}
-
-
-/* Print bug-reporting information in the help message. */
-static char *
-more_help (int key, const char *text, void *input)
-{
- char *tp = NULL;
- switch (key)
- {
- case ARGP_KEY_HELP_EXTRA:
- /* We print some extra information. */
- if (asprintf (&tp, gettext ("\
-For bug reporting instructions, please see:\n\
-%s.\n"), REPORT_BUGS_TO) < 0)
- return NULL;
- return tp;
- default:
- break;
- }
- return (char *) text;
-}
-
-/* Print the version information. */
-static void
-print_version (FILE *stream, struct argp_state *state)
-{
- fprintf (stream, "pldd %s%s\n", PKGVERSION, VERSION);
- fprintf (stream, gettext ("\
-Copyright (C) %s Free Software Foundation, Inc.\n\
-This is free software; see the source for copying conditions. There is NO\n\
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\
-"), "2017");
- fprintf (stream, gettext ("Written by %s.\n"), "Ulrich Drepper");
-}
-
-
-#define CLASS 32
-#include "pldd-xx.c"
-#define CLASS 64
-#include "pldd-xx.c"
-
-
-static int
-get_process_info (int dfd, long int pid)
-{
- memfd = openat (dfd, "mem", O_RDONLY);
- if (memfd == -1)
- goto no_info;
-
- int fd = openat (dfd, "exe", O_RDONLY);
- if (fd == -1)
- {
- no_info:
- error (0, errno, gettext ("cannot get information about process %lu"),
- pid);
- return EXIT_FAILURE;
- }
-
- char e_ident[EI_NIDENT];
- if (read (fd, e_ident, EI_NIDENT) != EI_NIDENT)
- goto no_info;
-
- close (fd);
-
- if (memcmp (e_ident, ELFMAG, SELFMAG) != 0)
- {
- error (0, 0, gettext ("process %lu is no ELF program"), pid);
- return EXIT_FAILURE;
- }
-
- fd = openat (dfd, "auxv", O_RDONLY);
- if (fd == -1)
- goto no_info;
-
- size_t auxv_size = 0;
- void *auxv = NULL;
- while (1)
- {
- auxv_size += 512;
- auxv = xrealloc (auxv, auxv_size);
-
- ssize_t n = pread (fd, auxv, auxv_size, 0);
- if (n < 0)
- goto no_info;
- if (n < auxv_size)
- {
- auxv_size = n;
- break;
- }
- }
-
- close (fd);
-
- int retval;
- if (e_ident[EI_CLASS] == ELFCLASS32)
- retval = find_maps32 (pid, auxv, auxv_size);
- else
- retval = find_maps64 (pid, auxv, auxv_size);
-
- free (auxv);
- close (memfd);
-
- return retval;
-}
diff --git a/elf/preloadtest.c b/elf/preloadtest.c
deleted file mode 100644
index 7ea10b9b5b..0000000000
--- a/elf/preloadtest.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include <stdio.h>
-
-#include "testobj.h"
-
-int
-main (void)
-{
- int res = preload (42);
-
- printf ("preload (42) = %d, %s\n", res, res == 92 ? "ok" : "wrong");
-
- return res != 92;
-}
-
-int
-foo (int a)
-{
- return a;
-}
diff --git a/elf/readelflib.c b/elf/readelflib.c
deleted file mode 100644
index 9ad56dcc34..0000000000
--- a/elf/readelflib.c
+++ /dev/null
@@ -1,234 +0,0 @@
-/* Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Andreas Jaeger <aj@suse.de>, 1999 and
- Jakub Jelinek <jakub@redhat.com>, 1999.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This code is a heavily simplified version of the readelf program
- that's part of the current binutils development version. For architectures
- which need to handle both 32bit and 64bit ELF libraries, this file is
- included twice for each arch size. */
-
-/* check_ptr checks that a pointer is in the mmaped file and doesn't
- point outside it. */
-#undef check_ptr
-#define check_ptr(ptr) \
-do \
- { \
- if ((void *)(ptr) < file_contents \
- || (void *)(ptr) > (file_contents+file_length)) \
- { \
- error (0, 0, _("file %s is truncated\n"), file_name); \
- return 1; \
- } \
- } \
- while (0);
-
-/* Returns 0 if everything is ok, != 0 in case of error. */
-int
-process_elf_file (const char *file_name, const char *lib, int *flag,
- unsigned int *osversion, char **soname, void *file_contents,
- size_t file_length)
-{
- int i;
- unsigned int j;
- ElfW(Addr) loadaddr;
- unsigned int dynamic_addr;
- size_t dynamic_size;
- char *program_interpreter;
-
- ElfW(Ehdr) *elf_header;
- ElfW(Phdr) *elf_pheader, *segment;
- ElfW(Dyn) *dynamic_segment, *dyn_entry;
- char *dynamic_strings;
-
- elf_header = (ElfW(Ehdr) *) file_contents;
- *osversion = 0;
-
- if (elf_header->e_ident [EI_CLASS] != ElfW (CLASS))
- {
- if (opt_verbose)
- {
- if (elf_header->e_ident [EI_CLASS] == ELFCLASS32)
- error (0, 0, _("%s is a 32 bit ELF file.\n"), file_name);
- else if (elf_header->e_ident [EI_CLASS] == ELFCLASS64)
- error (0, 0, _("%s is a 64 bit ELF file.\n"), file_name);
- else
- error (0, 0, _("Unknown ELFCLASS in file %s.\n"), file_name);
- }
- return 1;
- }
-
- if (elf_header->e_type != ET_DYN)
- {
- error (0, 0, _("%s is not a shared object file (Type: %d).\n"), file_name,
- elf_header->e_type);
- return 1;
- }
-
- /* Get information from elf program header. */
- elf_pheader = (ElfW(Phdr) *) (elf_header->e_phoff + file_contents);
- check_ptr (elf_pheader);
-
- /* The library is an elf library, now search for soname and
- libc5/libc6. */
- *flag = FLAG_ELF;
-
- loadaddr = -1;
- dynamic_addr = 0;
- dynamic_size = 0;
- program_interpreter = NULL;
- for (i = 0, segment = elf_pheader;
- i < elf_header->e_phnum; i++, segment++)
- {
- check_ptr (segment);
-
- switch (segment->p_type)
- {
- case PT_LOAD:
- if (loadaddr == (ElfW(Addr)) -1)
- loadaddr = segment->p_vaddr - segment->p_offset;
- break;
-
- case PT_DYNAMIC:
- if (dynamic_addr)
- error (0, 0, _("more than one dynamic segment\n"));
-
- dynamic_addr = segment->p_offset;
- dynamic_size = segment->p_filesz;
- break;
-
- case PT_INTERP:
- program_interpreter = (char *) (file_contents + segment->p_offset);
- check_ptr (program_interpreter);
-
- /* Check if this is enough to classify the binary. */
- for (j = 0; j < sizeof (interpreters) / sizeof (interpreters [0]);
- ++j)
- if (strcmp (program_interpreter, interpreters[j].soname) == 0)
- {
- *flag = interpreters[j].flag;
- break;
- }
- break;
-
- case PT_NOTE:
- if (!*osversion && segment->p_filesz >= 32 && segment->p_align >= 4)
- {
- ElfW(Word) *abi_note = (ElfW(Word) *) (file_contents
- + segment->p_offset);
- ElfW(Addr) size = segment->p_filesz;
-
- while (abi_note [0] != 4 || abi_note [1] != 16
- || abi_note [2] != 1
- || memcmp (abi_note + 3, "GNU", 4) != 0)
- {
-#define ROUND(len) (((len) + sizeof (ElfW(Word)) - 1) & -sizeof (ElfW(Word)))
- ElfW(Addr) note_size = 3 * sizeof (ElfW(Word))
- + ROUND (abi_note[0])
- + ROUND (abi_note[1]);
-
- if (size - 32 < note_size || note_size == 0)
- {
- size = 0;
- break;
- }
- size -= note_size;
- abi_note = (void *) abi_note + note_size;
- }
-
- if (size == 0)
- break;
-
- *osversion = (abi_note [4] << 24) |
- ((abi_note [5] & 0xff) << 16) |
- ((abi_note [6] & 0xff) << 8) |
- (abi_note [7] & 0xff);
- }
- break;
-
- default:
- break;
- }
-
- }
- if (loadaddr == (ElfW(Addr)) -1)
- {
- /* Very strange. */
- loadaddr = 0;
- }
-
- /* Now we can read the dynamic sections. */
- if (dynamic_size == 0)
- return 1;
-
- dynamic_segment = (ElfW(Dyn) *) (file_contents + dynamic_addr);
- check_ptr (dynamic_segment);
-
- /* Find the string table. */
- dynamic_strings = NULL;
- for (dyn_entry = dynamic_segment; dyn_entry->d_tag != DT_NULL;
- ++dyn_entry)
- {
- check_ptr (dyn_entry);
- if (dyn_entry->d_tag == DT_STRTAB)
- {
- dynamic_strings = (char *) (file_contents + dyn_entry->d_un.d_val - loadaddr);
- check_ptr (dynamic_strings);
- break;
- }
- }
-
- if (dynamic_strings == NULL)
- return 1;
-
- /* Now read the DT_NEEDED and DT_SONAME entries. */
- for (dyn_entry = dynamic_segment; dyn_entry->d_tag != DT_NULL;
- ++dyn_entry)
- {
- if (dyn_entry->d_tag == DT_NEEDED || dyn_entry->d_tag == DT_SONAME)
- {
- char *name = dynamic_strings + dyn_entry->d_un.d_val;
- check_ptr (name);
-
- if (dyn_entry->d_tag == DT_NEEDED)
- {
-
- if (*flag == FLAG_ELF)
- {
- /* Check if this is enough to classify the binary. */
- for (j = 0;
- j < sizeof (known_libs) / sizeof (known_libs [0]);
- ++j)
- if (strcmp (name, known_libs [j].soname) == 0)
- {
- *flag = known_libs [j].flag;
- break;
- }
- }
- }
-
- else if (dyn_entry->d_tag == DT_SONAME)
- *soname = xstrdup (name);
-
- /* Do we have everything we need? */
- if (*soname && *flag != FLAG_ELF)
- return 0;
- }
- }
-
- return 0;
-}
diff --git a/elf/readlib.c b/elf/readlib.c
deleted file mode 100644
index d278a189b2..0000000000
--- a/elf/readlib.c
+++ /dev/null
@@ -1,212 +0,0 @@
-/* Copyright (C) 1999-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Andreas Jaeger <aj@suse.de>, 1999 and
- Jakub Jelinek <jakub@redhat.com>, 1999.
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published
- by the Free Software Foundation; version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, see <http://www.gnu.org/licenses/>. */
-
-/* The code in this file and in readelflib is a heavily simplified
- version of the readelf program that's part of the current binutils
- development version. Besides the simplification, it has also been
- modified to read some other file formats. */
-
-#include <a.out.h>
-#include <elf.h>
-#include <error.h>
-#include <libintl.h>
-#include <link.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-#include <gnu/lib-names.h>
-
-#include <ldconfig.h>
-
-#define Elf32_CLASS ELFCLASS32
-#define Elf64_CLASS ELFCLASS64
-
-struct known_names
-{
- const char *soname;
- int flag;
-};
-
-static struct known_names interpreters[] =
-{
- { "/lib/" LD_SO, FLAG_ELF_LIBC6 },
-#ifdef SYSDEP_KNOWN_INTERPRETER_NAMES
- SYSDEP_KNOWN_INTERPRETER_NAMES
-#endif
-};
-
-static struct known_names known_libs[] =
-{
- { LIBC_SO, FLAG_ELF_LIBC6 },
- { LIBM_SO, FLAG_ELF_LIBC6 },
-#ifdef SYSDEP_KNOWN_LIBRARY_NAMES
- SYSDEP_KNOWN_LIBRARY_NAMES
-#endif
-};
-
-
-/* Check if string corresponds to a GDB Python file. */
-static bool
-is_gdb_python_file (const char *name)
-{
- size_t len = strlen (name);
- return len > 7 && strcmp (name + len - 7, "-gdb.py") == 0;
-}
-
-/* Returns 0 if everything is ok, != 0 in case of error. */
-int
-process_file (const char *real_file_name, const char *file_name,
- const char *lib, int *flag, unsigned int *osversion,
- char **soname, int is_link, struct stat64 *stat_buf)
-{
- FILE *file;
- struct stat64 statbuf;
- void *file_contents;
- int ret;
- ElfW(Ehdr) *elf_header;
- struct exec *aout_header;
-
- ret = 0;
- *flag = FLAG_ANY;
- *soname = NULL;
-
- file = fopen (real_file_name, "rb");
- if (file == NULL)
- {
- /* No error for stale symlink. */
- if (is_link && strstr (file_name, ".so") != NULL)
- return 1;
- error (0, 0, _("Input file %s not found.\n"), file_name);
- return 1;
- }
-
- if (fstat64 (fileno (file), &statbuf) < 0)
- {
- error (0, 0, _("Cannot fstat file %s.\n"), file_name);
- fclose (file);
- return 1;
- }
-
- /* Check that the file is large enough so that we can access the
- information. We're only checking the size of the headers here. */
- if ((size_t) statbuf.st_size < sizeof (struct exec)
- || (size_t) statbuf.st_size < sizeof (ElfW(Ehdr)))
- {
- if (statbuf.st_size == 0)
- error (0, 0, _("File %s is empty, not checked."), file_name);
- else
- {
- char buf[SELFMAG];
- size_t n = MIN (statbuf.st_size, SELFMAG);
- if (fread (buf, n, 1, file) == 1 && memcmp (buf, ELFMAG, n) == 0)
- error (0, 0, _("File %s is too small, not checked."), file_name);
- }
- fclose (file);
- return 1;
- }
-
- file_contents = mmap (0, statbuf.st_size, PROT_READ, MAP_SHARED,
- fileno (file), 0);
- if (file_contents == MAP_FAILED)
- {
- error (0, 0, _("Cannot mmap file %s.\n"), file_name);
- fclose (file);
- return 1;
- }
-
- /* First check if this is an aout file. */
- aout_header = (struct exec *) file_contents;
- if (N_MAGIC (*aout_header) == ZMAGIC
-#ifdef QMAGIC /* Linuxism. */
- || N_MAGIC (*aout_header) == QMAGIC
-#endif
- )
- {
- /* Aout files don't have a soname, just return the name
- including the major number. */
- char *copy, *major, *dot;
- copy = xstrdup (lib);
- major = strstr (copy, ".so.");
- if (major)
- {
- dot = strstr (major + 4, ".");
- if (dot)
- *dot = '\0';
- }
- *soname = copy;
- *flag = FLAG_LIBC4;
- goto done;
- }
-
- elf_header = (ElfW(Ehdr) *) file_contents;
- if (memcmp (elf_header->e_ident, ELFMAG, SELFMAG) != 0)
- {
- /* The file is neither ELF nor aout. Check if it's a linker
- script, like libc.so - otherwise complain. Only search the
- beginning of the file. */
- size_t len = MIN (statbuf.st_size, 512);
- if (memmem (file_contents, len, "GROUP", 5) == NULL
- && memmem (file_contents, len, "GNU ld script", 13) == NULL
- && !is_gdb_python_file (file_name))
- error (0, 0, _("%s is not an ELF file - it has the wrong magic bytes at the start.\n"),
- file_name);
- ret = 1;
- }
- /* Libraries have to be shared object files. */
- else if (elf_header->e_type != ET_DYN)
- ret = 1;
- else if (process_elf_file (file_name, lib, flag, osversion, soname,
- file_contents, statbuf.st_size))
- ret = 1;
-
- done:
- /* Clean up allocated memory and resources. */
- munmap (file_contents, statbuf.st_size);
- fclose (file);
-
- *stat_buf = statbuf;
- return ret;
-}
-
-/* Returns made up soname if lib doesn't have explicit DT_SONAME. */
-
-char *
-implicit_soname (const char *lib, int flag)
-{
- char *soname = xstrdup (lib);
-
- if ((flag & FLAG_TYPE_MASK) != FLAG_LIBC4)
- return soname;
-
- /* Aout files don't have a soname, just return the name
- including the major number. */
- char *major = strstr (soname, ".so.");
- if (major)
- {
- char *dot = strstr (major + 4, ".");
- if (dot)
- *dot = '\0';
- }
- return soname;
-}
-
-/* Get architecture specific version of process_elf_file. */
-#include <readelflib.c>
diff --git a/elf/reldep.c b/elf/reldep.c
deleted file mode 100644
index adabc0d5d5..0000000000
--- a/elf/reldep.c
+++ /dev/null
@@ -1,111 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- int (*fp) (void);
- int *vp;
-
- mtrace ();
-
- /* Open the two objects. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so: %s\n", dlerror ());
- exit (1);
- }
- h2 = dlopen ("reldepmod2.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldepmod2.so: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the address of the variable in reldepmod1.so. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\": %s\n", dlerror ());
- exit (1);
- }
-
- *vp = 42;
-
- /* Get the function `call_me' in the second object. This has a
- dependency which is resolved by a definition in reldepmod1.so. */
- fp = dlsym (h2, "call_me");
- if (fp == NULL)
- {
- printf ("cannot get address of \"call_me\": %s\n", dlerror ());
- exit (1);
- }
-
- /* Call the function. */
- if (fp () != 0)
- {
- puts ("function \"call_me\" returned wrong result");
- exit (1);
- }
-
- /* Now close the first object. If must still be around since we have
- an implicit dependency. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Try calling the function again. This will fail if the first object
- got unloaded. */
- if (fp () != 0)
- {
- puts ("second call of function \"call_me\" returned wrong result");
- exit (1);
- }
-
- /* Now close the second file as well. */
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Finally, open the first object again. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so the second time: %s\n", dlerror ());
- exit (1);
- }
-
- /* And get the variable address again. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\" the second time: %s\n",
- dlerror ());
- exit (1);
- }
-
- /* The variable now must have its originial value. */
- if (*vp != 0)
- {
- puts ("variable \"some_var\" not reset");
- exit (1);
- }
-
- /* Close the first object again, we are done. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep2.c b/elf/reldep2.c
deleted file mode 100644
index ba5ab222f9..0000000000
--- a/elf/reldep2.c
+++ /dev/null
@@ -1,101 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- int (*fp) (void);
- int *vp;
-
- mtrace ();
-
- /* Open the two objects. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so: %s\n", dlerror ());
- exit (1);
- }
- h2 = dlopen ("reldepmod3.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldepmod3.so: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the address of the variable in reldepmod1.so. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\": %s\n", dlerror ());
- exit (1);
- }
-
- *vp = 42;
-
- /* Get the function `call_me' in the second object. This has a
- dependency which is resolved by a definition in reldepmod1.so. */
- fp = dlsym (h2, "call_me");
- if (fp == NULL)
- {
- printf ("cannot get address of \"call_me\": %s\n", dlerror ());
- exit (1);
- }
-
- /* Call the function. */
- if (fp () != 0)
- {
- puts ("function \"call_me\" returned wrong result");
- exit (1);
- }
-
- /* Now close the first object. It must still be around since we have
- an implicit dependency. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Open the first object again. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so the second time: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the variable address again. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\" the second time: %s\n",
- dlerror ());
- exit (1);
- }
-
- /* The variable now must have its originial value. */
- if (*vp != 42)
- {
- puts ("variable \"some_var\" reset");
- exit (1);
- }
-
- /* Close the first object again, we are done. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep3.c b/elf/reldep3.c
deleted file mode 100644
index 05013d3509..0000000000
--- a/elf/reldep3.c
+++ /dev/null
@@ -1,101 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- int (*fp) (void);
- int *vp;
-
- mtrace ();
-
- /* Open the two objects. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so: %s\n", dlerror ());
- exit (1);
- }
- h2 = dlopen ("reldepmod4.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldepmod4.so: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the address of the variable in reldepmod1.so. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\": %s\n", dlerror ());
- exit (1);
- }
-
- *vp = 42;
-
- /* Get the function `call_me' in the second object. This has a
- dependency which is resolved by a definition in reldepmod1.so. */
- fp = dlsym (h2, "call_me");
- if (fp == NULL)
- {
- printf ("cannot get address of \"call_me\": %s\n", dlerror ());
- exit (1);
- }
-
- /* Call the function. */
- if (fp () != 0)
- {
- puts ("function \"call_me\" returned wrong result");
- exit (1);
- }
-
- /* Now close the first object. If must still be around since we have
- an implicit dependency. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Open the first object again. */
- h1 = dlopen ("reldepmod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod1.so the second time: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the variable address again. */
- vp = dlsym (h1, "some_var");
- if (vp == NULL)
- {
- printf ("cannot get address of \"some_var\" the second time: %s\n",
- dlerror ());
- exit (1);
- }
-
- /* The variable now must have its originial value. */
- if (*vp != 0)
- {
- puts ("variable \"some_var\" not reset");
- exit (1);
- }
-
- /* Close the first object again, we are done. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep4.c b/elf/reldep4.c
deleted file mode 100644
index ba12e7d9c4..0000000000
--- a/elf/reldep4.c
+++ /dev/null
@@ -1,40 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- int i;
- void *h1, *h2;
-
- mtrace ();
-
- for (i = 0; i < 3; i++)
- {
- h1 = dlopen ("reldep4mod1.so", RTLD_NOW | RTLD_GLOBAL);
- if (h1 == NULL)
- {
- printf ("cannot open reldep4mod1.so: %s\n", dlerror ());
- exit (1);
- }
- h2 = dlopen ("reldep4mod2.so", RTLD_NOW | RTLD_GLOBAL);
- if (h2 == NULL)
- {
- printf ("cannot open reldep4mod2.so: %s\n", dlerror ());
- exit (1);
- }
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
- }
- return 0;
-}
diff --git a/elf/reldep4mod1.c b/elf/reldep4mod1.c
deleted file mode 100644
index 934a68096e..0000000000
--- a/elf/reldep4mod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-int foo (void);
-
-int foo (void)
-{
- return 0;
-}
-
diff --git a/elf/reldep4mod2.c b/elf/reldep4mod2.c
deleted file mode 100644
index 26ce6bf13a..0000000000
--- a/elf/reldep4mod2.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int foo (void);
-extern int bar (void);
-
-int
-bar (void)
-{
- return foo ();
-}
diff --git a/elf/reldep4mod3.c b/elf/reldep4mod3.c
deleted file mode 100644
index 934a68096e..0000000000
--- a/elf/reldep4mod3.c
+++ /dev/null
@@ -1,7 +0,0 @@
-int foo (void);
-
-int foo (void)
-{
- return 0;
-}
-
diff --git a/elf/reldep4mod4.c b/elf/reldep4mod4.c
deleted file mode 100644
index 26ce6bf13a..0000000000
--- a/elf/reldep4mod4.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int foo (void);
-extern int bar (void);
-
-int
-bar (void)
-{
- return foo ();
-}
diff --git a/elf/reldep5.c b/elf/reldep5.c
deleted file mode 100644
index 881d519ff6..0000000000
--- a/elf/reldep5.c
+++ /dev/null
@@ -1,70 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- int (*fp) (void);
-
- mtrace ();
-
- /* Open the two objects. */
- h1 = dlopen ("reldepmod5.so", RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open reldepmod5.so: %s\n", dlerror ());
- exit (1);
- }
- h2 = dlopen ("reldepmod6.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldepmod6.so: %s\n", dlerror ());
- exit (1);
- }
-
- /* Get the address of the variable in reldepmod1.so. */
- fp = dlsym (h2, "bar");
- if (fp == NULL)
- {
- printf ("cannot get address of \"bar\": %s\n", dlerror ());
- exit (1);
- }
-
- /* Call the function. */
- puts ("calling fp for the first time");
- if (fp () != 0)
- {
- puts ("function \"call_me\" returned wrong result");
- exit (1);
- }
-
- /* Now close the first object. It must still be around since we have
- an implicit dependency. */
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Calling the function must still work. */
- puts ("calling fp for the second time");
- if (fp () != 0)
- {
- puts ("function \"call_me\" the second time returned wrong result");
- exit (1);
- }
- puts ("second call suceeded as well");
-
- /* Close the second object, we are done. */
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep6.c b/elf/reldep6.c
deleted file mode 100644
index 1eeec6c862..0000000000
--- a/elf/reldep6.c
+++ /dev/null
@@ -1,109 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-typedef int (*fn)(void);
-#define CHUNKS 1024
-#define REPEAT 64
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- fn **foopp;
- fn bar, baz;
- int i, j;
- int n;
- void *allocs[REPEAT][CHUNKS];
-
- mtrace ();
-
- /* Open the two objects. */
- h1 = dlopen ("reldep6mod3.so", RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open reldep6mod3.so: %s\n", dlerror ());
- exit (1);
- }
-
- foopp = dlsym (h1, "foopp");
- if (foopp == NULL)
- {
- printf ("cannot get address of \"foopp\": %s\n", dlerror ());
- exit (1);
- }
- n = (**foopp) ();
- if (n != 20)
- {
- printf ("(**foopp)() return %d, not return 20\n", n);
- exit (1);
- }
-
- h2 = dlopen ("reldep6mod4.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldep6mod4.so: %s\n", dlerror ());
- exit (1);
- }
-
- baz = dlsym (h2, "baz");
- if (baz == NULL)
- {
- printf ("cannot get address of \"baz\": %s\n", dlerror ());
- exit (1);
- }
- if (baz () != 31)
- {
- printf ("baz() did not return 31\n");
- exit (1);
- }
-
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- /* Clobber memory. */
- for (i = 0; i < REPEAT; ++i)
- for (j = 0; j < CHUNKS; ++j)
- allocs[i][j] = calloc (1, j + 1);
-
- bar = dlsym (h2, "bar");
- if (bar == NULL)
- {
- printf ("cannot get address of \"bar\": %s\n", dlerror ());
- exit (1);
- }
- if (bar () != 40)
- {
- printf ("bar() did not return 40\n");
- exit (1);
- }
-
- baz = dlsym (h2, "baz");
- if (baz == NULL)
- {
- printf ("cannot get address of \"baz\": %s\n", dlerror ());
- exit (1);
- }
- if (baz () != 31)
- {
- printf ("baz() did not return 31\n");
- exit (1);
- }
-
- for (i = 0; i < REPEAT; ++i)
- for (j = 0; j < CHUNKS; ++j)
- free (allocs[i][j]);
-
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep6mod0.c b/elf/reldep6mod0.c
deleted file mode 100644
index 58f3745fb4..0000000000
--- a/elf/reldep6mod0.c
+++ /dev/null
@@ -1,8 +0,0 @@
-int bar (void);
-extern void free (void *);
-
-int bar (void)
-{
- free (0);
- return 40;
-}
diff --git a/elf/reldep6mod1.c b/elf/reldep6mod1.c
deleted file mode 100644
index 037a73a198..0000000000
--- a/elf/reldep6mod1.c
+++ /dev/null
@@ -1,14 +0,0 @@
-int foo (void);
-int baz (void);
-extern int weak (void);
-asm (".weak weak");
-
-int foo (void)
-{
- return 20;
-}
-
-int baz (void)
-{
- return weak () + 1;
-}
diff --git a/elf/reldep6mod2.c b/elf/reldep6mod2.c
deleted file mode 100644
index c2ef3f9bc0..0000000000
--- a/elf/reldep6mod2.c
+++ /dev/null
@@ -1,3 +0,0 @@
-extern int foo (void);
-
-void *foop = (void *) foo;
diff --git a/elf/reldep6mod3.c b/elf/reldep6mod3.c
deleted file mode 100644
index 881828ef6e..0000000000
--- a/elf/reldep6mod3.c
+++ /dev/null
@@ -1,3 +0,0 @@
-extern void *foop;
-
-void **foopp = &foop;
diff --git a/elf/reldep6mod4.c b/elf/reldep6mod4.c
deleted file mode 100644
index 8fa89de64b..0000000000
--- a/elf/reldep6mod4.c
+++ /dev/null
@@ -1,12 +0,0 @@
-int foo (void);
-int weak (void);
-
-int foo (void)
-{
- return 10;
-}
-
-int weak (void)
-{
- return 30;
-}
diff --git a/elf/reldep7.c b/elf/reldep7.c
deleted file mode 100644
index 5275a0e8f1..0000000000
--- a/elf/reldep7.c
+++ /dev/null
@@ -1,58 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- void *h2;
- void *mod1_bar, *mod2_bar;
-
- h1 = dlopen ("reldep7mod1.so", RTLD_GLOBAL | RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open reldep7mod1.so: %s\n", dlerror ());
- exit (1);
- }
-
- h2 = dlopen ("reldep7mod2.so", RTLD_GLOBAL | RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open reldep7mod1.so: %s\n", dlerror ());
- exit (1);
- }
-
- mod1_bar = dlsym (h1, "mod1_bar");
- if (mod1_bar == NULL)
- {
- printf ("cannot get address of \"mod1_bar\": %s\n", dlerror ());
- exit (1);
- }
-
- mod2_bar = dlsym (h2, "mod2_bar");
- if (mod2_bar == NULL)
- {
- printf ("cannot get address of \"mod2_bar\": %s\n", dlerror ());
- exit (1);
- }
-
- printf ("%d\n", ((int (*) (void)) mod1_bar) ());
- printf ("%d\n", ((int (*) (void)) mod2_bar) ());
-
- if (dlclose (h1) != 0)
- {
- printf ("closing h1 failed: %s\n", dlerror ());
- exit (1);
- }
-
- printf ("%d\n", ((int (*) (void)) mod2_bar) ());
-
- if (dlclose (h2) != 0)
- {
- printf ("closing h2 failed: %s\n", dlerror ());
- exit (1);
- }
-
- return 0;
-}
diff --git a/elf/reldep7mod1.c b/elf/reldep7mod1.c
deleted file mode 100644
index de1bb3a6cd..0000000000
--- a/elf/reldep7mod1.c
+++ /dev/null
@@ -1,12 +0,0 @@
-int foo (void) __attribute__ ((weak));
-int
-foo (void)
-{
- return 1;
-}
-
-int
-mod1_bar (void)
-{
- return foo ();
-}
diff --git a/elf/reldep7mod2.c b/elf/reldep7mod2.c
deleted file mode 100644
index 3fa3368792..0000000000
--- a/elf/reldep7mod2.c
+++ /dev/null
@@ -1,12 +0,0 @@
-int foo (void) __attribute__ ((weak));
-int
-foo (void)
-{
- return 2;
-}
-
-int
-mod2_bar (void)
-{
- return foo ();
-}
diff --git a/elf/reldep8.c b/elf/reldep8.c
deleted file mode 100644
index 90009a5609..0000000000
--- a/elf/reldep8.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-#include <stdlib.h>
-#include <dlfcn.h>
-
-int
-main (void)
-{
- void *handle = dlopen ("reldep8mod3.so", RTLD_LAZY);
- if (handle == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- dlclose (handle);
- abort ();
-}
diff --git a/elf/reldep8mod1.c b/elf/reldep8mod1.c
deleted file mode 100644
index acddc4cf8b..0000000000
--- a/elf/reldep8mod1.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include <stdlib.h>
-void
-foo (void)
-{
- exit (0);
-}
-
-void
-__attribute__((destructor))
-bar (void)
-{
- static int i;
- foo ();
- ++i;
-}
-void
-baz (void)
-{
-}
diff --git a/elf/reldep8mod2.c b/elf/reldep8mod2.c
deleted file mode 100644
index d0020240a8..0000000000
--- a/elf/reldep8mod2.c
+++ /dev/null
@@ -1,7 +0,0 @@
-void
-__attribute__((constructor))
-xxx (void)
-{
- extern void baz (void);
- baz ();
-}
diff --git a/elf/reldep8mod3.c b/elf/reldep8mod3.c
deleted file mode 100644
index 6d1a0d47b7..0000000000
--- a/elf/reldep8mod3.c
+++ /dev/null
@@ -1 +0,0 @@
-int x;
diff --git a/elf/reldep9.c b/elf/reldep9.c
deleted file mode 100644
index 51c7a8bb9e..0000000000
--- a/elf/reldep9.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-#include <stdlib.h>
-#include <dlfcn.h>
-
-int
-main (void)
-{
- void *handle = dlopen ("reldep9mod3.so", RTLD_LAZY);
- if (handle == NULL)
- {
- printf ("%s\n", dlerror ());
- exit (1);
- }
- dlclose (handle);
- abort ();
-}
diff --git a/elf/reldep9mod1.c b/elf/reldep9mod1.c
deleted file mode 100644
index 249a2bae1c..0000000000
--- a/elf/reldep9mod1.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <stdlib.h>
-void
-foo (void)
-{
- exit (0);
-}
-
-void
-__attribute__((destructor))
-bar (void)
-{
- static int i;
- foo ();
- ++i;
-}
-
-void
-__attribute__((constructor))
-destr (void)
-{
- extern void baz (void);
- baz ();
-}
diff --git a/elf/reldep9mod2.c b/elf/reldep9mod2.c
deleted file mode 100644
index 090966e3e3..0000000000
--- a/elf/reldep9mod2.c
+++ /dev/null
@@ -1,3 +0,0 @@
-void baz (void)
-{
-}
diff --git a/elf/reldep9mod3.c b/elf/reldep9mod3.c
deleted file mode 100644
index 6d1a0d47b7..0000000000
--- a/elf/reldep9mod3.c
+++ /dev/null
@@ -1 +0,0 @@
-int x;
diff --git a/elf/reldepmod1.c b/elf/reldepmod1.c
deleted file mode 100644
index b8ef6401e1..0000000000
--- a/elf/reldepmod1.c
+++ /dev/null
@@ -1,10 +0,0 @@
-extern int foo (void);
-
-int some_var;
-
-
-int
-foo (void)
-{
- return some_var;
-}
diff --git a/elf/reldepmod2.c b/elf/reldepmod2.c
deleted file mode 100644
index b7edebae80..0000000000
--- a/elf/reldepmod2.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int foo (void);
-extern int call_me (void);
-
-int
-call_me (void)
-{
- return foo () - 42;
-}
diff --git a/elf/reldepmod3.c b/elf/reldepmod3.c
deleted file mode 100644
index 66a996cd90..0000000000
--- a/elf/reldepmod3.c
+++ /dev/null
@@ -1,20 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-extern int call_me (void);
-
-int
-call_me (void)
-{
- int (*fp) (void);
-
- fp = dlsym (RTLD_DEFAULT, "foo");
- if (fp == NULL)
- {
- printf ("cannot get address of foo in global scope: %s\n", dlerror ());
- exit (1);
- }
-
- return fp () - 42;
-}
diff --git a/elf/reldepmod4.c b/elf/reldepmod4.c
deleted file mode 100644
index dcb503bba7..0000000000
--- a/elf/reldepmod4.c
+++ /dev/null
@@ -1,37 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-extern int call_me (void);
-
-int
-call_me (void)
-{
- void *h;
- int (*fp) (void);
- int res;
-
- h = dlopen ("reldepmod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open reldepmod1.so in %s: %s\n", __FILE__, dlerror ());
- exit (1);
- }
-
- fp = dlsym (h, "foo");
- if (fp == NULL)
- {
- printf ("cannot get address of foo in global scope: %s\n", dlerror ());
- exit (1);
- }
-
- res = fp () - 42;
-
- if (dlclose (h) != 0)
- {
- printf ("failure when closing h in %s: %s\n", __FILE__, dlerror ());
- exit (1);
- }
-
- return res;
-}
diff --git a/elf/reldepmod5.c b/elf/reldepmod5.c
deleted file mode 100644
index 62df697162..0000000000
--- a/elf/reldepmod5.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int foo (void);
-
-int
-foo (void)
-{
- return 42;
-}
diff --git a/elf/reldepmod6.c b/elf/reldepmod6.c
deleted file mode 100644
index cd2aeb400d..0000000000
--- a/elf/reldepmod6.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern int call_me (void);
-extern int bar (void);
-
-int
-bar (void)
-{
- return call_me ();
-}
diff --git a/elf/resolvfail.c b/elf/resolvfail.c
deleted file mode 100644
index ebd635d153..0000000000
--- a/elf/resolvfail.c
+++ /dev/null
@@ -1,31 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-static const char obj[] = "testobj1.so";
-
-int
-main (void)
-{
- void *d = dlopen (obj, RTLD_LAZY);
- int n;
-
- if (d == NULL)
- {
- printf ("cannot load %s: %s\n", obj, dlerror ());
- return 1;
- }
-
- for (n = 0; n < 10000; ++n)
- if (dlsym (d, "does not exist") != NULL)
- {
- puts ("dlsym() did not fail");
- return 1;
- }
- else if (dlerror () == NULL)
- {
- puts ("dlerror() didn't return a string");
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/restest1.c b/elf/restest1.c
deleted file mode 100644
index eb5aeca59e..0000000000
--- a/elf/restest1.c
+++ /dev/null
@@ -1,57 +0,0 @@
-#include <dlfcn.h>
-#include <error.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-main (void)
-{
- void *h1;
- int (*fp1) (int);
- void *h2;
- int (*fp2) (int);
- int res1;
- int res2;
-
- mtrace ();
-
- h1 = dlopen ("testobj1.so", RTLD_LAZY);
- if (h1 == NULL)
- error (EXIT_FAILURE, 0, "while loading `%s': %s", "testobj1.so",
- dlerror ());
-
- h2 = dlopen ("testobj1_1.so", RTLD_LAZY);
- if (h1 == NULL)
- error (EXIT_FAILURE, 0, "while loading `%s': %s", "testobj1_1.so",
- dlerror ());
-
- fp1 = dlsym (h1, "obj1func1");
- if (fp1 == NULL)
- error (EXIT_FAILURE, 0, "getting `obj1func1' in `%s': %s",
- "testobj1.so", dlerror ());
-
- fp2 = dlsym (h2, "obj1func1");
- if (fp2 == NULL)
- error (EXIT_FAILURE, 0, "getting `obj1func1' in `%s': %s",
- "testobj1_1.so", dlerror ());
-
- res1 = fp1 (10);
- res2 = fp2 (10);
- printf ("fp1(10) = %d\nfp2(10) = %d\n", res1, res2);
-
- if (dlclose (h1) != 0)
- error (EXIT_FAILURE, 0, "cannot close testobj1.so: %s\n", dlerror ());
- if (dlclose (h2) != 0)
- error (EXIT_FAILURE, 0, "cannot close testobj1_1.so: %s\n", dlerror ());
-
- return res1 != 42 || res2 != 72;
-}
-
-
-extern int foo (int a);
-int
-foo (int a)
-{
- return a + 10;
-}
diff --git a/elf/restest2.c b/elf/restest2.c
deleted file mode 100644
index f959f030a0..0000000000
--- a/elf/restest2.c
+++ /dev/null
@@ -1,33 +0,0 @@
-#include <sys/types.h>
-#include <dlfcn.h>
-#include <error.h>
-#include <mcheck.h>
-#include <stdlib.h>
-#include <unistd.h>
-
-pid_t pid, pid2;
-
-pid_t getpid(void)
-{
- pid_t (*f)(void);
- f = (pid_t (*)(void)) dlsym (RTLD_NEXT, "getpid");
- if (f == NULL)
- error (EXIT_FAILURE, 0, "dlsym (RTLD_NEXT, \"getpid\"): %s", dlerror ());
- return (pid2 = f()) + 26;
-}
-
-int
-main (void)
-{
- pid_t (*f)(void);
-
- mtrace ();
-
- f = (pid_t (*)(void)) dlsym (RTLD_DEFAULT, "getpid");
- if (f == NULL)
- error (EXIT_FAILURE, 0, "dlsym (RTLD_DEFAULT, \"getpid\"): %s", dlerror ());
- pid = f();
- if (pid != pid2 + 26)
- error (EXIT_FAILURE, 0, "main getpid() not called");
- return 0;
-}
diff --git a/elf/rtld-Rules b/elf/rtld-Rules
deleted file mode 100644
index 2c7b99828c..0000000000
--- a/elf/rtld-Rules
+++ /dev/null
@@ -1,149 +0,0 @@
-# Subroutine makefile for compiling libc modules linked into dynamic linker.
-
-# Copyright (C) 2002-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-# This makefile is never used by itself, but only from the rtld-libc.a
-# rule in Makefile, which does make -f librtld.mk -f rtld-Rules.
-# librtld.mk is the generated file containing variable definitions for
-# `rtld-subdirs', a subset of the top-level $(subdirs) list; and for each
-# SUBDIR in $(rtld-subdirs), `rtld-SUBDIR' listing `module.os' file names.
-
-.PHONY: rtld-all
-rtld-all:
-
-# When run from the elf/Makefile to build rtld-libc.a, $(subdir) is elf.
-ifneq ($(subdir),elf)
-ifndef rtld-modules
-error rtld-modules not set
-endif
-endif
-
-ifndef rtld-modules
-# Running to build rtld-libc.a, driving runs of $(rtld-subdir-make), below.
-
-ifndef rtld-subdirs
-error This makefile is a subroutine of elf/Makefile not to be used directly
-endif
-
-include ../Makeconfig
-
-rtld-all: $(objpfx)rtld-libc.a
-
-$(objpfx)rtld-libc.a: $(foreach dir,$(rtld-subdirs),\
- $(addprefix $(common-objpfx)$(dir)/rtld-,\
- $(rtld-$(dir))))
- @-rm -f $@T
- $(AR) cq$(verbose) $@T $^
- mv -f $@T $@
-
-# Use the verbose option of ar and tar when not running silently.
-ifeq "$(findstring s,$(MAKEFLAGS))" "" # if not -s
-verbose := v
-else # -s
-verbose :=
-endif # not -s
-
-
-# For each subdirectory, define a pattern rule that makes all of that
-# subdirectory's modules at once with one recursive make command.
-object-suffixes-left := $(rtld-subdirs)
-define o-iterator-doit
-$(foreach obj,$(rtld-$o),$(common-objpfx)%/rtld-$(obj)): FORCE ; \
- +$$(rtld-subdir-make)
-endef
-include $(patsubst %,../o-iterator.mk,$(object-suffixes-left))
-
-# This is how we descend into each subdirectory. See below.
-define rtld-subdir-make
-$(MAKE) $(subdir-args) objdir=$(objdir) \
- -f Makefile -f ../elf/rtld-Rules rtld-all \
- rtld-modules='$(addprefix rtld-,$(rtld-$*))'
-endef
-
-# See subdir-target-args in ../Makefile for the model.
-subdir-args = subdir=$*$(if $($*-srcdir),\
- -C $($*-srcdir) ..=`pwd`/,\
- -C $(..)$* ..=../)
-
-FORCE:
-
-else
-
-# In this case we are being run by $(rtld-subdir-make), above.
-# Some other subdir's Makefile has provided all its normal rules,
-# and we just provide some additional definitions.
-
-rtld-compile-command.S = $(compile-command.S) $(rtld-CPPFLAGS)
-rtld-compile-command.s = $(compile-command.s) $(rtld-CPPFLAGS)
-rtld-compile-command.c = $(compile-command.c) $(rtld-CPPFLAGS) $(rtld-CFLAGS)
-
-# These are the basic compilation rules corresponding to the Makerules ones.
-# The sysd-rules generated makefile already defines pattern rules for rtld-%
-# targets built from sysdeps source files.
-$(objpfx)rtld-%.os: rtld-%.S $(before-compile)
- $(rtld-compile-command.S)
-$(objpfx)rtld-%.os: rtld-%.s $(before-compile)
- $(rtld-compile-command.s)
-$(objpfx)rtld-%.os: rtld-%.c $(before-compile)
- $(rtld-compile-command.c)
-$(objpfx)rtld-%.os: %.S $(before-compile)
- $(rtld-compile-command.S)
-$(objpfx)rtld-%.os: %.s $(before-compile)
- $(rtld-compile-command.s)
-$(objpfx)rtld-%.os: %.c $(before-compile)
- $(rtld-compile-command.c)
-
-# The rules for generated source files.
-$(objpfx)rtld-%.os: $(objpfx)rtld-%.S $(before-compile)
- $(rtld-compile-command.S)
-$(objpfx)rtld-%.os: $(objpfx)rtld-%.s $(before-compile)
- $(rtld-compile-command.s)
-$(objpfx)rtld-%.os: $(objpfx)rtld-%.c $(before-compile)
- $(rtld-compile-command.c)
-$(objpfx)rtld-%.os: $(objpfx)%.S $(before-compile)
- $(rtld-compile-command.S)
-$(objpfx)rtld-%.os: $(objpfx)%.s $(before-compile)
- $(rtld-compile-command.s)
-$(objpfx)rtld-%.os: $(objpfx)%.c $(before-compile)
- $(rtld-compile-command.c)
-
-# The command line setting of rtld-modules (see above) tells us
-# what we need to build, and that tells us what dependency files we need.
-rtld-all: $(addprefix $(objpfx),$(rtld-modules))
-
-# Figure out the dependency files we need. After respecting the $(omit-deps)
-# list as applied to the names without the `rtld-', there may be none left.
-rtld-depfiles := $(patsubst %,$(objpfx)rtld-%.os.d,\
- $(filter-out $(omit-deps),\
- $(rtld-modules:rtld-%.os=%)))
-rtld-depfiles := $(strip $(wildcard $(rtld-depfiles)) \
- $(patsubst %.dt,%.d,\
- $(wildcard $(rtld-depfiles:.d=.dt))))
-ifdef rtld-depfiles
--include $(rtld-depfiles)
-endif
-
-# This here is the whole point of all the shenanigans.
-# Set libof-* for each routine.
-cpp-srcs-left := $(rtld-modules:%.os=%)
-lib := rtld
-include $(patsubst %,$(..)libof-iterator.mk,$(cpp-srcs-left))
-
-rtld-CFLAGS += $(no-stack-protector)
-
-endif
diff --git a/elf/rtld-debugger-interface.txt b/elf/rtld-debugger-interface.txt
deleted file mode 100644
index 61bc99e4b0..0000000000
--- a/elf/rtld-debugger-interface.txt
+++ /dev/null
@@ -1,122 +0,0 @@
-Standard debugger interface
-===========================
-
-The run-time linker exposes a rendezvous structure to allow debuggers
-to interface with it. This structure, r_debug, is defined in link.h.
-If the executable's dynamic section has a DT_DEBUG element, the
-run-time linker sets that element's value to the address where this
-structure can be found.
-
-The r_debug structure contains (amongst others) the following fields:
-
- struct link_map *r_map:
- A linked list of loaded objects.
-
- enum { RT_CONSISTENT, RT_ADD, RT_DELETE } r_state:
- The current state of the r_map list. RT_CONSISTENT means that r_map
- is not currently being modified and may safely be inspected. RT_ADD
- means that an object is being added to r_map, and that the list is
- not guaranteed to be consistent. Likewise RT_DELETE means that an
- object is being removed from the list.
-
- ElfW(Addr) r_brk:
- The address of a function internal to the run-time linker which is
- called whenever r_state is changed. The debugger should set a
- breakpoint at this address if it wants to notice mapping changes.
-
-This protocol is widely supported, but somewhat limited in that it
-has no provision to provide access to multiple namespaces, and that
-the notifications (via r_brk) only refer to changes to r_map--the
-debugger is notified that a new object has been added, for instance,
-but there is no way for the debugger to discover whether any of the
-objects in the link-map have been relocated or not.
-
-
-Probe-based debugger interface
-==============================
-
-Systemtap is a dynamic tracing/instrumenting tool available on Linux.
-Probes that are not fired at run time have close to zero overhead.
-glibc contains a number of probes that debuggers can set breakpoints
-on in order to notice certain events.
-
-All rtld probes have the following arguments:
-
- arg1: Lmid_t lmid:
- The link-map ID of the link-map list that the object was loaded
- into. This will be LM_ID_BASE for the application's main link-map
- list, or some other value for different namespaces.
-
- arg2: struct r_debug *r_debug:
- A pointer to the r_debug structure containing the link-map list
- that the object was loaded into. This will be the value stored in
- DT_DEBUG for the application's main link-map list, or some other
- value for different namespaces.
-
-map_complete and reloc_complete may have the following additional
-argument:
-
- arg3: struct link_map *new:
- A pointer which, if not NULL, points to the entry in the specified
- r_debug structure's link-map list corresponding to the first new
- object to have been mapped or relocated, with new->l_next pointing
- to the link-map of the next new object to have been mapped or
- relocated, and so on. Note that because `new' is an entry in a
- larger list, new->l_prev (if not NULL) will point to what was the
- last link-map in the link-map list prior to the new objects being
- mapped or relocated.
-
-The following probes are available:
-
- init_start:
- This is called once, when the linker is about to fill in the main
- r_debug structure at application startup. init_start always has
- lmid set to LM_ID_BASE and r_debug set to the value stored in
- DT_DEBUG. r_debug is not guaranteed to be consistent until
- init_complete is fired.
-
- init_complete:
- This is called once, when the linker has filled in the main
- r_debug structure at application startup. init_complete always
- has lmid set to LM_ID_BASE and r_debug set to the value stored
- in DT_DEBUG. The r_debug structure is consistent and may be
- inspected, and all objects in the link-map are guaranteed to
- have been relocated.
-
- map_start:
- The linker is about to map new objects into the specified
- namespace. The namespace's r_debug structure is not guaranteed
- to be consistent until a corresponding map_complete is fired.
-
- map_complete:
- The linker has finished mapping new objects into the specified
- namespace. The namespace's r_debug structure is consistent and
- may be inspected, although objects in the namespace's link-map
- are not guaranteed to have been relocated.
-
- map_failed:
- The linker failed while attempting to map new objects into
- the specified namespace. The namespace's r_debug structure
- is consistent and may be inspected.
-
- reloc_start:
- The linker is about to relocate all unrelocated objects in the
- specified namespace. The namespace's r_debug structure is not
- guaranteed to be consistent until a corresponding reloc_complete
- is fired.
-
- reloc_complete:
- The linker has relocated all objects in the specified namespace.
- The namespace's r_debug structure is consistent and may be
- inspected, and all objects in the namespace's link-map are
- guaranteed to have been relocated.
-
- unmap_start:
- The linker is about to remove objects from the specified
- namespace. The namespace's r_debug structure is not guaranteed to
- be consistent until a corresponding unmap_complete is fired.
-
- unmap_complete:
- The linker has finished removing objects into the specified
- namespace. The namespace's r_debug structure is consistent and
- may be inspected.
diff --git a/elf/rtld.c b/elf/rtld.c
deleted file mode 100644
index 3746653afb..0000000000
--- a/elf/rtld.c
+++ /dev/null
@@ -1,2652 +0,0 @@
-/* Run time dynamic linker.
- Copyright (C) 1995-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <dlfcn.h>
-#include <fcntl.h>
-#include <stdbool.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-#include <ldsodefs.h>
-#include <_itoa.h>
-#include <entry.h>
-#include <fpu_control.h>
-#include <hp-timing.h>
-#include <libc-lock.h>
-#include "dynamic-link.h"
-#include <dl-librecon.h>
-#include <unsecvars.h>
-#include <dl-cache.h>
-#include <dl-osinfo.h>
-#include <dl-procinfo.h>
-#include <tls.h>
-#include <stap-probe.h>
-#include <stackinfo.h>
-
-#include <assert.h>
-
-/* Avoid PLT use for our local calls at startup. */
-extern __typeof (__mempcpy) __mempcpy attribute_hidden;
-
-/* GCC has mental blocks about _exit. */
-extern __typeof (_exit) exit_internal asm ("_exit") attribute_hidden;
-#define _exit exit_internal
-
-/* Helper function to handle errors while resolving symbols. */
-static void print_unresolved (int errcode, const char *objname,
- const char *errsting);
-
-/* Helper function to handle errors when a version is missing. */
-static void print_missing_version (int errcode, const char *objname,
- const char *errsting);
-
-/* Print the various times we collected. */
-static void print_statistics (hp_timing_t *total_timep);
-
-/* Add audit objects. */
-static void process_dl_audit (char *str);
-
-/* This is a list of all the modes the dynamic loader can be in. */
-enum mode { normal, list, verify, trace };
-
-/* Process all environments variables the dynamic linker must recognize.
- Since all of them start with `LD_' we are a bit smarter while finding
- all the entries. */
-static void process_envvars (enum mode *modep);
-
-#ifdef DL_ARGV_NOT_RELRO
-int _dl_argc attribute_hidden;
-char **_dl_argv = NULL;
-/* Nonzero if we were run directly. */
-unsigned int _dl_skip_args attribute_hidden;
-#else
-int _dl_argc attribute_relro attribute_hidden;
-char **_dl_argv attribute_relro = NULL;
-unsigned int _dl_skip_args attribute_relro attribute_hidden;
-#endif
-rtld_hidden_data_def (_dl_argv)
-
-#ifndef THREAD_SET_STACK_GUARD
-/* Only exported for architectures that don't store the stack guard canary
- in thread local area. */
-uintptr_t __stack_chk_guard attribute_relro;
-#endif
-
-/* Only exported for architectures that don't store the pointer guard
- value in thread local area. */
-uintptr_t __pointer_chk_guard_local
- attribute_relro attribute_hidden __attribute__ ((nocommon));
-#ifndef THREAD_SET_POINTER_GUARD
-strong_alias (__pointer_chk_guard_local, __pointer_chk_guard)
-#endif
-
-
-/* List of auditing DSOs. */
-static struct audit_list
-{
- const char *name;
- struct audit_list *next;
-} *audit_list;
-
-#ifndef HAVE_INLINED_SYSCALLS
-/* Set nonzero during loading and initialization of executable and
- libraries, cleared before the executable's entry point runs. This
- must not be initialized to nonzero, because the unused dynamic
- linker loaded in for libc.so's "ld.so.1" dep will provide the
- definition seen by libc.so's initializer; that value must be zero,
- and will be since that dynamic linker's _dl_start and dl_main will
- never be called. */
-int _dl_starting_up = 0;
-rtld_hidden_def (_dl_starting_up)
-#endif
-
-/* This is the structure which defines all variables global to ld.so
- (except those which cannot be added for some reason). */
-struct rtld_global _rtld_global =
- {
- /* Generally the default presumption without further information is an
- * executable stack but this is not true for all platforms. */
- ._dl_stack_flags = DEFAULT_STACK_PERMS,
-#ifdef _LIBC_REENTRANT
- ._dl_load_lock = _RTLD_LOCK_RECURSIVE_INITIALIZER,
- ._dl_load_write_lock = _RTLD_LOCK_RECURSIVE_INITIALIZER,
-#endif
- ._dl_nns = 1,
- ._dl_ns =
- {
-#ifdef _LIBC_REENTRANT
- [LM_ID_BASE] = { ._ns_unique_sym_table
- = { .lock = _RTLD_LOCK_RECURSIVE_INITIALIZER } }
-#endif
- }
- };
-/* If we would use strong_alias here the compiler would see a
- non-hidden definition. This would undo the effect of the previous
- declaration. So spell out was strong_alias does plus add the
- visibility attribute. */
-extern struct rtld_global _rtld_local
- __attribute__ ((alias ("_rtld_global"), visibility ("hidden")));
-
-
-/* This variable is similar to _rtld_local, but all values are
- read-only after relocation. */
-struct rtld_global_ro _rtld_global_ro attribute_relro =
- {
- /* Get architecture specific initializer. */
-#include <dl-procinfo.c>
-#ifdef NEED_DL_SYSINFO
- ._dl_sysinfo = DL_SYSINFO_DEFAULT,
-#endif
- ._dl_debug_fd = STDERR_FILENO,
- ._dl_use_load_bias = -2,
- ._dl_correct_cache_id = _DL_CACHE_DEFAULT_ID,
-#if !HAVE_TUNABLES
- ._dl_hwcap_mask = HWCAP_IMPORTANT,
-#endif
- ._dl_lazy = 1,
- ._dl_fpu_control = _FPU_DEFAULT,
- ._dl_pagesize = EXEC_PAGESIZE,
- ._dl_inhibit_cache = 0,
-
- /* Function pointers. */
- ._dl_debug_printf = _dl_debug_printf,
- ._dl_mcount = _dl_mcount,
- ._dl_lookup_symbol_x = _dl_lookup_symbol_x,
- ._dl_check_caller = _dl_check_caller,
- ._dl_open = _dl_open,
- ._dl_close = _dl_close,
- ._dl_tls_get_addr_soft = _dl_tls_get_addr_soft,
-#ifdef HAVE_DL_DISCOVER_OSVERSION
- ._dl_discover_osversion = _dl_discover_osversion
-#endif
- };
-/* If we would use strong_alias here the compiler would see a
- non-hidden definition. This would undo the effect of the previous
- declaration. So spell out was strong_alias does plus add the
- visibility attribute. */
-extern struct rtld_global_ro _rtld_local_ro
- __attribute__ ((alias ("_rtld_global_ro"), visibility ("hidden")));
-
-
-static void dl_main (const ElfW(Phdr) *phdr, ElfW(Word) phnum,
- ElfW(Addr) *user_entry, ElfW(auxv_t) *auxv);
-
-/* These two variables cannot be moved into .data.rel.ro. */
-static struct libname_list _dl_rtld_libname;
-static struct libname_list _dl_rtld_libname2;
-
-/* Variable for statistics. */
-#ifndef HP_TIMING_NONAVAIL
-static hp_timing_t relocate_time;
-static hp_timing_t load_time attribute_relro;
-static hp_timing_t start_time attribute_relro;
-#endif
-
-/* Additional definitions needed by TLS initialization. */
-#ifdef TLS_INIT_HELPER
-TLS_INIT_HELPER
-#endif
-
-/* Helper function for syscall implementation. */
-#ifdef DL_SYSINFO_IMPLEMENTATION
-DL_SYSINFO_IMPLEMENTATION
-#endif
-
-/* Before ld.so is relocated we must not access variables which need
- relocations. This means variables which are exported. Variables
- declared as static are fine. If we can mark a variable hidden this
- is fine, too. The latter is important here. We can avoid setting
- up a temporary link map for ld.so if we can mark _rtld_global as
- hidden. */
-#ifdef PI_STATIC_AND_HIDDEN
-# define DONT_USE_BOOTSTRAP_MAP 1
-#endif
-
-#ifdef DONT_USE_BOOTSTRAP_MAP
-static ElfW(Addr) _dl_start_final (void *arg);
-#else
-struct dl_start_final_info
-{
- struct link_map l;
-#if !defined HP_TIMING_NONAVAIL && HP_TIMING_INLINE
- hp_timing_t start_time;
-#endif
-};
-static ElfW(Addr) _dl_start_final (void *arg,
- struct dl_start_final_info *info);
-#endif
-
-/* These defined magically in the linker script. */
-extern char _begin[] attribute_hidden;
-extern char _etext[] attribute_hidden;
-extern char _end[] attribute_hidden;
-
-
-#ifdef RTLD_START
-RTLD_START
-#else
-# error "sysdeps/MACHINE/dl-machine.h fails to define RTLD_START"
-#endif
-
-/* This is the second half of _dl_start (below). It can be inlined safely
- under DONT_USE_BOOTSTRAP_MAP, where it is careful not to make any GOT
- references. When the tools don't permit us to avoid using a GOT entry
- for _dl_rtld_global (no attribute_hidden support), we must make sure
- this function is not inlined (see below). */
-
-#ifdef DONT_USE_BOOTSTRAP_MAP
-static inline ElfW(Addr) __attribute__ ((always_inline))
-_dl_start_final (void *arg)
-#else
-static ElfW(Addr) __attribute__ ((noinline))
-_dl_start_final (void *arg, struct dl_start_final_info *info)
-#endif
-{
- ElfW(Addr) start_addr;
-
- if (HP_SMALL_TIMING_AVAIL)
- {
- /* If it hasn't happen yet record the startup time. */
- if (! HP_TIMING_INLINE)
- HP_TIMING_NOW (start_time);
-#if !defined DONT_USE_BOOTSTRAP_MAP && !defined HP_TIMING_NONAVAIL
- else
- start_time = info->start_time;
-#endif
- }
-
- /* Transfer data about ourselves to the permanent link_map structure. */
-#ifndef DONT_USE_BOOTSTRAP_MAP
- GL(dl_rtld_map).l_addr = info->l.l_addr;
- GL(dl_rtld_map).l_ld = info->l.l_ld;
- memcpy (GL(dl_rtld_map).l_info, info->l.l_info,
- sizeof GL(dl_rtld_map).l_info);
- GL(dl_rtld_map).l_mach = info->l.l_mach;
- GL(dl_rtld_map).l_relocated = 1;
-#endif
- _dl_setup_hash (&GL(dl_rtld_map));
- GL(dl_rtld_map).l_real = &GL(dl_rtld_map);
- GL(dl_rtld_map).l_map_start = (ElfW(Addr)) _begin;
- GL(dl_rtld_map).l_map_end = (ElfW(Addr)) _end;
- GL(dl_rtld_map).l_text_end = (ElfW(Addr)) _etext;
- /* Copy the TLS related data if necessary. */
-#ifndef DONT_USE_BOOTSTRAP_MAP
-# if NO_TLS_OFFSET != 0
- GL(dl_rtld_map).l_tls_offset = NO_TLS_OFFSET;
-# endif
-#endif
-
- HP_TIMING_NOW (GL(dl_cpuclock_offset));
-
- /* Initialize the stack end variable. */
- __libc_stack_end = __builtin_frame_address (0);
-
- /* Call the OS-dependent function to set up life so we can do things like
- file access. It will call `dl_main' (below) to do all the real work
- of the dynamic linker, and then unwind our frame and run the user
- entry point on the same stack we entered on. */
- start_addr = _dl_sysdep_start (arg, &dl_main);
-
-#ifndef HP_TIMING_NONAVAIL
- hp_timing_t rtld_total_time;
- if (HP_SMALL_TIMING_AVAIL)
- {
- hp_timing_t end_time;
-
- /* Get the current time. */
- HP_TIMING_NOW (end_time);
-
- /* Compute the difference. */
- HP_TIMING_DIFF (rtld_total_time, start_time, end_time);
- }
-#endif
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_STATISTICS))
- {
-#ifndef HP_TIMING_NONAVAIL
- print_statistics (&rtld_total_time);
-#else
- print_statistics (NULL);
-#endif
- }
-
- return start_addr;
-}
-
-static ElfW(Addr) __attribute_used__ internal_function
-_dl_start (void *arg)
-{
-#ifdef DONT_USE_BOOTSTRAP_MAP
-# define bootstrap_map GL(dl_rtld_map)
-#else
- struct dl_start_final_info info;
-# define bootstrap_map info.l
-#endif
-
- /* This #define produces dynamic linking inline functions for
- bootstrap relocation instead of general-purpose relocation.
- Since ld.so must not have any undefined symbols the result
- is trivial: always the map of ld.so itself. */
-#define RTLD_BOOTSTRAP
-#define RESOLVE_MAP(sym, version, flags) (&bootstrap_map)
-#include "dynamic-link.h"
-
- if (HP_TIMING_INLINE && HP_SMALL_TIMING_AVAIL)
-#ifdef DONT_USE_BOOTSTRAP_MAP
- HP_TIMING_NOW (start_time);
-#else
- HP_TIMING_NOW (info.start_time);
-#endif
-
- /* Partly clean the `bootstrap_map' structure up. Don't use
- `memset' since it might not be built in or inlined and we cannot
- make function calls at this point. Use '__builtin_memset' if we
- know it is available. We do not have to clear the memory if we
- do not have to use the temporary bootstrap_map. Global variables
- are initialized to zero by default. */
-#ifndef DONT_USE_BOOTSTRAP_MAP
-# ifdef HAVE_BUILTIN_MEMSET
- __builtin_memset (bootstrap_map.l_info, '\0', sizeof (bootstrap_map.l_info));
-# else
- for (size_t cnt = 0;
- cnt < sizeof (bootstrap_map.l_info) / sizeof (bootstrap_map.l_info[0]);
- ++cnt)
- bootstrap_map.l_info[cnt] = 0;
-# endif
-#endif
-
- /* Figure out the run-time load address of the dynamic linker itself. */
- bootstrap_map.l_addr = elf_machine_load_address ();
-
- /* Read our own dynamic section and fill in the info array. */
- bootstrap_map.l_ld = (void *) bootstrap_map.l_addr + elf_machine_dynamic ();
- elf_get_dynamic_info (&bootstrap_map, NULL);
-
-#if NO_TLS_OFFSET != 0
- bootstrap_map.l_tls_offset = NO_TLS_OFFSET;
-#endif
-
-#ifdef ELF_MACHINE_BEFORE_RTLD_RELOC
- ELF_MACHINE_BEFORE_RTLD_RELOC (bootstrap_map.l_info);
-#endif
-
- if (bootstrap_map.l_addr || ! bootstrap_map.l_info[VALIDX(DT_GNU_PRELINKED)])
- {
- /* Relocate ourselves so we can do normal function calls and
- data access using the global offset table. */
-
- ELF_DYNAMIC_RELOCATE (&bootstrap_map, 0, 0, 0);
- }
- bootstrap_map.l_relocated = 1;
-
- /* Please note that we don't allow profiling of this object and
- therefore need not test whether we have to allocate the array
- for the relocation results (as done in dl-reloc.c). */
-
- /* Now life is sane; we can call functions and access global data.
- Set up to use the operating system facilities, and find out from
- the operating system's program loader where to find the program
- header table in core. Put the rest of _dl_start into a separate
- function, that way the compiler cannot put accesses to the GOT
- before ELF_DYNAMIC_RELOCATE. */
- {
-#ifdef DONT_USE_BOOTSTRAP_MAP
- ElfW(Addr) entry = _dl_start_final (arg);
-#else
- ElfW(Addr) entry = _dl_start_final (arg, &info);
-#endif
-
-#ifndef ELF_MACHINE_START_ADDRESS
-# define ELF_MACHINE_START_ADDRESS(map, start) (start)
-#endif
-
- return ELF_MACHINE_START_ADDRESS (GL(dl_ns)[LM_ID_BASE]._ns_loaded, entry);
- }
-}
-
-
-
-/* Now life is peachy; we can do all normal operations.
- On to the real work. */
-
-/* Some helper functions. */
-
-/* Arguments to relocate_doit. */
-struct relocate_args
-{
- struct link_map *l;
- int reloc_mode;
-};
-
-struct map_args
-{
- /* Argument to map_doit. */
- const char *str;
- struct link_map *loader;
- int mode;
- /* Return value of map_doit. */
- struct link_map *map;
-};
-
-struct dlmopen_args
-{
- const char *fname;
- struct link_map *map;
-};
-
-struct lookup_args
-{
- const char *name;
- struct link_map *map;
- void *result;
-};
-
-/* Arguments to version_check_doit. */
-struct version_check_args
-{
- int doexit;
- int dotrace;
-};
-
-static void
-relocate_doit (void *a)
-{
- struct relocate_args *args = (struct relocate_args *) a;
-
- _dl_relocate_object (args->l, args->l->l_scope, args->reloc_mode, 0);
-}
-
-static void
-map_doit (void *a)
-{
- struct map_args *args = (struct map_args *) a;
- int type = (args->mode == __RTLD_OPENEXEC) ? lt_executable : lt_library;
- args->map = _dl_map_object (args->loader, args->str, type, 0,
- args->mode, LM_ID_BASE);
-}
-
-static void
-dlmopen_doit (void *a)
-{
- struct dlmopen_args *args = (struct dlmopen_args *) a;
- args->map = _dl_open (args->fname,
- (RTLD_LAZY | __RTLD_DLOPEN | __RTLD_AUDIT
- | __RTLD_SECURE),
- dl_main, LM_ID_NEWLM, _dl_argc, _dl_argv,
- __environ);
-}
-
-static void
-lookup_doit (void *a)
-{
- struct lookup_args *args = (struct lookup_args *) a;
- const ElfW(Sym) *ref = NULL;
- args->result = NULL;
- lookup_t l = _dl_lookup_symbol_x (args->name, args->map, &ref,
- args->map->l_local_scope, NULL, 0,
- DL_LOOKUP_RETURN_NEWEST, NULL);
- if (ref != NULL)
- args->result = DL_SYMBOL_ADDRESS (l, ref);
-}
-
-static void
-version_check_doit (void *a)
-{
- struct version_check_args *args = (struct version_check_args *) a;
- if (_dl_check_all_versions (GL(dl_ns)[LM_ID_BASE]._ns_loaded, 1,
- args->dotrace) && args->doexit)
- /* We cannot start the application. Abort now. */
- _exit (1);
-}
-
-
-static inline struct link_map *
-find_needed (const char *name)
-{
- struct r_scope_elem *scope = &GL(dl_ns)[LM_ID_BASE]._ns_loaded->l_searchlist;
- unsigned int n = scope->r_nlist;
-
- while (n-- > 0)
- if (_dl_name_match_p (name, scope->r_list[n]))
- return scope->r_list[n];
-
- /* Should never happen. */
- return NULL;
-}
-
-static int
-match_version (const char *string, struct link_map *map)
-{
- const char *strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
- ElfW(Verdef) *def;
-
-#define VERDEFTAG (DT_NUM + DT_THISPROCNUM + DT_VERSIONTAGIDX (DT_VERDEF))
- if (map->l_info[VERDEFTAG] == NULL)
- /* The file has no symbol versioning. */
- return 0;
-
- def = (ElfW(Verdef) *) ((char *) map->l_addr
- + map->l_info[VERDEFTAG]->d_un.d_ptr);
- while (1)
- {
- ElfW(Verdaux) *aux = (ElfW(Verdaux) *) ((char *) def + def->vd_aux);
-
- /* Compare the version strings. */
- if (strcmp (string, strtab + aux->vda_name) == 0)
- /* Bingo! */
- return 1;
-
- /* If no more definitions we failed to find what we want. */
- if (def->vd_next == 0)
- break;
-
- /* Next definition. */
- def = (ElfW(Verdef) *) ((char *) def + def->vd_next);
- }
-
- return 0;
-}
-
-static bool tls_init_tp_called;
-
-static void *
-init_tls (void)
-{
- /* Number of elements in the static TLS block. */
- GL(dl_tls_static_nelem) = GL(dl_tls_max_dtv_idx);
-
- /* Do not do this twice. The audit interface might have required
- the DTV interfaces to be set up early. */
- if (GL(dl_initial_dtv) != NULL)
- return NULL;
-
- /* Allocate the array which contains the information about the
- dtv slots. We allocate a few entries more than needed to
- avoid the need for reallocation. */
- size_t nelem = GL(dl_tls_max_dtv_idx) + 1 + TLS_SLOTINFO_SURPLUS;
-
- /* Allocate. */
- GL(dl_tls_dtv_slotinfo_list) = (struct dtv_slotinfo_list *)
- calloc (sizeof (struct dtv_slotinfo_list)
- + nelem * sizeof (struct dtv_slotinfo), 1);
- /* No need to check the return value. If memory allocation failed
- the program would have been terminated. */
-
- struct dtv_slotinfo *slotinfo = GL(dl_tls_dtv_slotinfo_list)->slotinfo;
- GL(dl_tls_dtv_slotinfo_list)->len = nelem;
- GL(dl_tls_dtv_slotinfo_list)->next = NULL;
-
- /* Fill in the information from the loaded modules. No namespace
- but the base one can be filled at this time. */
- assert (GL(dl_ns)[LM_ID_BASE + 1]._ns_loaded == NULL);
- int i = 0;
- for (struct link_map *l = GL(dl_ns)[LM_ID_BASE]._ns_loaded; l != NULL;
- l = l->l_next)
- if (l->l_tls_blocksize != 0)
- {
- /* This is a module with TLS data. Store the map reference.
- The generation counter is zero. */
- slotinfo[i].map = l;
- /* slotinfo[i].gen = 0; */
- ++i;
- }
- assert (i == GL(dl_tls_max_dtv_idx));
-
- /* Compute the TLS offsets for the various blocks. */
- _dl_determine_tlsoffset ();
-
- /* Construct the static TLS block and the dtv for the initial
- thread. For some platforms this will include allocating memory
- for the thread descriptor. The memory for the TLS block will
- never be freed. It should be allocated accordingly. The dtv
- array can be changed if dynamic loading requires it. */
- void *tcbp = _dl_allocate_tls_storage ();
- if (tcbp == NULL)
- _dl_fatal_printf ("\
-cannot allocate TLS data structures for initial thread");
-
- /* Store for detection of the special case by __tls_get_addr
- so it knows not to pass this dtv to the normal realloc. */
- GL(dl_initial_dtv) = GET_DTV (tcbp);
-
- /* And finally install it for the main thread. */
- const char *lossage = TLS_INIT_TP (tcbp);
- if (__glibc_unlikely (lossage != NULL))
- _dl_fatal_printf ("cannot set up thread-local storage: %s\n", lossage);
- tls_init_tp_called = true;
-
- return tcbp;
-}
-
-static unsigned int
-do_preload (const char *fname, struct link_map *main_map, const char *where)
-{
- const char *objname;
- const char *err_str = NULL;
- struct map_args args;
- bool malloced;
-
- args.str = fname;
- args.loader = main_map;
- args.mode = __RTLD_SECURE;
-
- unsigned int old_nloaded = GL(dl_ns)[LM_ID_BASE]._ns_nloaded;
-
- (void) _dl_catch_error (&objname, &err_str, &malloced, map_doit, &args);
- if (__glibc_unlikely (err_str != NULL))
- {
- _dl_error_printf ("\
-ERROR: ld.so: object '%s' from %s cannot be preloaded (%s): ignored.\n",
- fname, where, err_str);
- /* No need to call free, this is still before
- the libc's malloc is used. */
- }
- else if (GL(dl_ns)[LM_ID_BASE]._ns_nloaded != old_nloaded)
- /* It is no duplicate. */
- return 1;
-
- /* Nothing loaded. */
- return 0;
-}
-
-#if defined SHARED && defined _LIBC_REENTRANT \
- && defined __rtld_lock_default_lock_recursive
-static void
-rtld_lock_default_lock_recursive (void *lock)
-{
- __rtld_lock_default_lock_recursive (lock);
-}
-
-static void
-rtld_lock_default_unlock_recursive (void *lock)
-{
- __rtld_lock_default_unlock_recursive (lock);
-}
-#endif
-
-
-static void
-security_init (void)
-{
- /* Set up the stack checker's canary. */
- uintptr_t stack_chk_guard = _dl_setup_stack_chk_guard (_dl_random);
-#ifdef THREAD_SET_STACK_GUARD
- THREAD_SET_STACK_GUARD (stack_chk_guard);
-#else
- __stack_chk_guard = stack_chk_guard;
-#endif
-
- /* Set up the pointer guard as well, if necessary. */
- uintptr_t pointer_chk_guard
- = _dl_setup_pointer_guard (_dl_random, stack_chk_guard);
-#ifdef THREAD_SET_POINTER_GUARD
- THREAD_SET_POINTER_GUARD (pointer_chk_guard);
-#endif
- __pointer_chk_guard_local = pointer_chk_guard;
-
- /* We do not need the _dl_random value anymore. The less
- information we leave behind, the better, so clear the
- variable. */
- _dl_random = NULL;
-}
-
-#include "setup-vdso.h"
-
-/* The library search path. */
-static const char *library_path attribute_relro;
-/* The list preloaded objects. */
-static const char *preloadlist attribute_relro;
-/* Nonzero if information about versions has to be printed. */
-static int version_info attribute_relro;
-
-static void
-dl_main (const ElfW(Phdr) *phdr,
- ElfW(Word) phnum,
- ElfW(Addr) *user_entry,
- ElfW(auxv_t) *auxv)
-{
- const ElfW(Phdr) *ph;
- enum mode mode;
- struct link_map *main_map;
- size_t file_size;
- char *file;
- bool has_interp = false;
- unsigned int i;
- bool prelinked = false;
- bool rtld_is_main = false;
-#ifndef HP_TIMING_NONAVAIL
- hp_timing_t start;
- hp_timing_t stop;
- hp_timing_t diff;
-#endif
- void *tcbp = NULL;
-
- GL(dl_init_static_tls) = &_dl_nothread_init_static_tls;
-
-#if defined SHARED && defined _LIBC_REENTRANT \
- && defined __rtld_lock_default_lock_recursive
- GL(dl_rtld_lock_recursive) = rtld_lock_default_lock_recursive;
- GL(dl_rtld_unlock_recursive) = rtld_lock_default_unlock_recursive;
-#endif
-
- /* The explicit initialization here is cheaper than processing the reloc
- in the _rtld_local definition's initializer. */
- GL(dl_make_stack_executable_hook) = &_dl_make_stack_executable;
-
- /* Process the environment variable which control the behaviour. */
- process_envvars (&mode);
-
-#ifndef HAVE_INLINED_SYSCALLS
- /* Set up a flag which tells we are just starting. */
- _dl_starting_up = 1;
-#endif
-
- if (*user_entry == (ElfW(Addr)) ENTRY_POINT)
- {
- /* Ho ho. We are not the program interpreter! We are the program
- itself! This means someone ran ld.so as a command. Well, that
- might be convenient to do sometimes. We support it by
- interpreting the args like this:
-
- ld.so PROGRAM ARGS...
-
- The first argument is the name of a file containing an ELF
- executable we will load and run with the following arguments.
- To simplify life here, PROGRAM is searched for using the
- normal rules for shared objects, rather than $PATH or anything
- like that. We just load it and use its entry point; we don't
- pay attention to its PT_INTERP command (we are the interpreter
- ourselves). This is an easy way to test a new ld.so before
- installing it. */
- rtld_is_main = true;
-
- /* Note the place where the dynamic linker actually came from. */
- GL(dl_rtld_map).l_name = rtld_progname;
-
- while (_dl_argc > 1)
- if (! strcmp (_dl_argv[1], "--list"))
- {
- mode = list;
- GLRO(dl_lazy) = -1; /* This means do no dependency analysis. */
-
- ++_dl_skip_args;
- --_dl_argc;
- ++_dl_argv;
- }
- else if (! strcmp (_dl_argv[1], "--verify"))
- {
- mode = verify;
-
- ++_dl_skip_args;
- --_dl_argc;
- ++_dl_argv;
- }
- else if (! strcmp (_dl_argv[1], "--inhibit-cache"))
- {
- GLRO(dl_inhibit_cache) = 1;
- ++_dl_skip_args;
- --_dl_argc;
- ++_dl_argv;
- }
- else if (! strcmp (_dl_argv[1], "--library-path")
- && _dl_argc > 2)
- {
- library_path = _dl_argv[2];
-
- _dl_skip_args += 2;
- _dl_argc -= 2;
- _dl_argv += 2;
- }
- else if (! strcmp (_dl_argv[1], "--inhibit-rpath")
- && _dl_argc > 2)
- {
- GLRO(dl_inhibit_rpath) = _dl_argv[2];
-
- _dl_skip_args += 2;
- _dl_argc -= 2;
- _dl_argv += 2;
- }
- else if (! strcmp (_dl_argv[1], "--audit") && _dl_argc > 2)
- {
- process_dl_audit (_dl_argv[2]);
-
- _dl_skip_args += 2;
- _dl_argc -= 2;
- _dl_argv += 2;
- }
- else
- break;
-
- /* If we have no further argument the program was called incorrectly.
- Grant the user some education. */
- if (_dl_argc < 2)
- _dl_fatal_printf ("\
-Usage: ld.so [OPTION]... EXECUTABLE-FILE [ARGS-FOR-PROGRAM...]\n\
-You have invoked `ld.so', the helper program for shared library executables.\n\
-This program usually lives in the file `/lib/ld.so', and special directives\n\
-in executable files using ELF shared libraries tell the system's program\n\
-loader to load the helper program from this file. This helper program loads\n\
-the shared libraries needed by the program executable, prepares the program\n\
-to run, and runs it. You may invoke this helper program directly from the\n\
-command line to load and run an ELF executable file; this is like executing\n\
-that file itself, but always uses this helper program from the file you\n\
-specified, instead of the helper program file specified in the executable\n\
-file you run. This is mostly of use for maintainers to test new versions\n\
-of this helper program; chances are you did not intend to run this program.\n\
-\n\
- --list list all dependencies and how they are resolved\n\
- --verify verify that given object really is a dynamically linked\n\
- object we can handle\n\
- --inhibit-cache Do not use " LD_SO_CACHE "\n\
- --library-path PATH use given PATH instead of content of the environment\n\
- variable LD_LIBRARY_PATH\n\
- --inhibit-rpath LIST ignore RUNPATH and RPATH information in object names\n\
- in LIST\n\
- --audit LIST use objects named in LIST as auditors\n");
-
- ++_dl_skip_args;
- --_dl_argc;
- ++_dl_argv;
-
- /* The initialization of _dl_stack_flags done below assumes the
- executable's PT_GNU_STACK may have been honored by the kernel, and
- so a PT_GNU_STACK with PF_X set means the stack started out with
- execute permission. However, this is not really true if the
- dynamic linker is the executable the kernel loaded. For this
- case, we must reinitialize _dl_stack_flags to match the dynamic
- linker itself. If the dynamic linker was built with a
- PT_GNU_STACK, then the kernel may have loaded us with a
- nonexecutable stack that we will have to make executable when we
- load the program below unless it has a PT_GNU_STACK indicating
- nonexecutable stack is ok. */
-
- for (ph = phdr; ph < &phdr[phnum]; ++ph)
- if (ph->p_type == PT_GNU_STACK)
- {
- GL(dl_stack_flags) = ph->p_flags;
- break;
- }
-
- if (__builtin_expect (mode, normal) == verify)
- {
- const char *objname;
- const char *err_str = NULL;
- struct map_args args;
- bool malloced;
-
- args.str = rtld_progname;
- args.loader = NULL;
- args.mode = __RTLD_OPENEXEC;
- (void) _dl_catch_error (&objname, &err_str, &malloced, map_doit,
- &args);
- if (__glibc_unlikely (err_str != NULL))
- /* We don't free the returned string, the programs stops
- anyway. */
- _exit (EXIT_FAILURE);
- }
- else
- {
- HP_TIMING_NOW (start);
- _dl_map_object (NULL, rtld_progname, lt_executable, 0,
- __RTLD_OPENEXEC, LM_ID_BASE);
- HP_TIMING_NOW (stop);
-
- HP_TIMING_DIFF (load_time, start, stop);
- }
-
- /* Now the map for the main executable is available. */
- main_map = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
-
- if (__builtin_expect (mode, normal) == normal
- && GL(dl_rtld_map).l_info[DT_SONAME] != NULL
- && main_map->l_info[DT_SONAME] != NULL
- && strcmp ((const char *) D_PTR (&GL(dl_rtld_map), l_info[DT_STRTAB])
- + GL(dl_rtld_map).l_info[DT_SONAME]->d_un.d_val,
- (const char *) D_PTR (main_map, l_info[DT_STRTAB])
- + main_map->l_info[DT_SONAME]->d_un.d_val) == 0)
- _dl_fatal_printf ("loader cannot load itself\n");
-
- phdr = main_map->l_phdr;
- phnum = main_map->l_phnum;
- /* We overwrite here a pointer to a malloc()ed string. But since
- the malloc() implementation used at this point is the dummy
- implementations which has no real free() function it does not
- makes sense to free the old string first. */
- main_map->l_name = (char *) "";
- *user_entry = main_map->l_entry;
-
-#ifdef HAVE_AUX_VECTOR
- /* Adjust the on-stack auxiliary vector so that it looks like the
- binary was executed directly. */
- for (ElfW(auxv_t) *av = auxv; av->a_type != AT_NULL; av++)
- switch (av->a_type)
- {
- case AT_PHDR:
- av->a_un.a_val = (uintptr_t) phdr;
- break;
- case AT_PHNUM:
- av->a_un.a_val = phnum;
- break;
- case AT_ENTRY:
- av->a_un.a_val = *user_entry;
- break;
- case AT_EXECFN:
- av->a_un.a_val = (uintptr_t) _dl_argv[0];
- break;
- }
-#endif
- }
- else
- {
- /* Create a link_map for the executable itself.
- This will be what dlopen on "" returns. */
- main_map = _dl_new_object ((char *) "", "", lt_executable, NULL,
- __RTLD_OPENEXEC, LM_ID_BASE);
- assert (main_map != NULL);
- main_map->l_phdr = phdr;
- main_map->l_phnum = phnum;
- main_map->l_entry = *user_entry;
-
- /* Even though the link map is not yet fully initialized we can add
- it to the map list since there are no possible users running yet. */
- _dl_add_to_namespace_list (main_map, LM_ID_BASE);
- assert (main_map == GL(dl_ns)[LM_ID_BASE]._ns_loaded);
-
- /* At this point we are in a bit of trouble. We would have to
- fill in the values for l_dev and l_ino. But in general we
- do not know where the file is. We also do not handle AT_EXECFD
- even if it would be passed up.
-
- We leave the values here defined to 0. This is normally no
- problem as the program code itself is normally no shared
- object and therefore cannot be loaded dynamically. Nothing
- prevent the use of dynamic binaries and in these situations
- we might get problems. We might not be able to find out
- whether the object is already loaded. But since there is no
- easy way out and because the dynamic binary must also not
- have an SONAME we ignore this program for now. If it becomes
- a problem we can force people using SONAMEs. */
-
- /* We delay initializing the path structure until we got the dynamic
- information for the program. */
- }
-
- main_map->l_map_end = 0;
- main_map->l_text_end = 0;
- /* Perhaps the executable has no PT_LOAD header entries at all. */
- main_map->l_map_start = ~0;
- /* And it was opened directly. */
- ++main_map->l_direct_opencount;
-
- /* Scan the program header table for the dynamic section. */
- for (ph = phdr; ph < &phdr[phnum]; ++ph)
- switch (ph->p_type)
- {
- case PT_PHDR:
- /* Find out the load address. */
- main_map->l_addr = (ElfW(Addr)) phdr - ph->p_vaddr;
- break;
- case PT_DYNAMIC:
- /* This tells us where to find the dynamic section,
- which tells us everything we need to do. */
- main_map->l_ld = (void *) main_map->l_addr + ph->p_vaddr;
- break;
- case PT_INTERP:
- /* This "interpreter segment" was used by the program loader to
- find the program interpreter, which is this program itself, the
- dynamic linker. We note what name finds us, so that a future
- dlopen call or DT_NEEDED entry, for something that wants to link
- against the dynamic linker as a shared library, will know that
- the shared object is already loaded. */
- _dl_rtld_libname.name = ((const char *) main_map->l_addr
- + ph->p_vaddr);
- /* _dl_rtld_libname.next = NULL; Already zero. */
- GL(dl_rtld_map).l_libname = &_dl_rtld_libname;
-
- /* Ordinarilly, we would get additional names for the loader from
- our DT_SONAME. This can't happen if we were actually linked as
- a static executable (detect this case when we have no DYNAMIC).
- If so, assume the filename component of the interpreter path to
- be our SONAME, and add it to our name list. */
- if (GL(dl_rtld_map).l_ld == NULL)
- {
- const char *p = NULL;
- const char *cp = _dl_rtld_libname.name;
-
- /* Find the filename part of the path. */
- while (*cp != '\0')
- if (*cp++ == '/')
- p = cp;
-
- if (p != NULL)
- {
- _dl_rtld_libname2.name = p;
- /* _dl_rtld_libname2.next = NULL; Already zero. */
- _dl_rtld_libname.next = &_dl_rtld_libname2;
- }
- }
-
- has_interp = true;
- break;
- case PT_LOAD:
- {
- ElfW(Addr) mapstart;
- ElfW(Addr) allocend;
-
- /* Remember where the main program starts in memory. */
- mapstart = (main_map->l_addr
- + (ph->p_vaddr & ~(GLRO(dl_pagesize) - 1)));
- if (main_map->l_map_start > mapstart)
- main_map->l_map_start = mapstart;
-
- /* Also where it ends. */
- allocend = main_map->l_addr + ph->p_vaddr + ph->p_memsz;
- if (main_map->l_map_end < allocend)
- main_map->l_map_end = allocend;
- if ((ph->p_flags & PF_X) && allocend > main_map->l_text_end)
- main_map->l_text_end = allocend;
- }
- break;
-
- case PT_TLS:
- if (ph->p_memsz > 0)
- {
- /* Note that in the case the dynamic linker we duplicate work
- here since we read the PT_TLS entry already in
- _dl_start_final. But the result is repeatable so do not
- check for this special but unimportant case. */
- main_map->l_tls_blocksize = ph->p_memsz;
- main_map->l_tls_align = ph->p_align;
- if (ph->p_align == 0)
- main_map->l_tls_firstbyte_offset = 0;
- else
- main_map->l_tls_firstbyte_offset = (ph->p_vaddr
- & (ph->p_align - 1));
- main_map->l_tls_initimage_size = ph->p_filesz;
- main_map->l_tls_initimage = (void *) ph->p_vaddr;
-
- /* This image gets the ID one. */
- GL(dl_tls_max_dtv_idx) = main_map->l_tls_modid = 1;
- }
- break;
-
- case PT_GNU_STACK:
- GL(dl_stack_flags) = ph->p_flags;
- break;
-
- case PT_GNU_RELRO:
- main_map->l_relro_addr = ph->p_vaddr;
- main_map->l_relro_size = ph->p_memsz;
- break;
- }
-
- /* Adjust the address of the TLS initialization image in case
- the executable is actually an ET_DYN object. */
- if (main_map->l_tls_initimage != NULL)
- main_map->l_tls_initimage
- = (char *) main_map->l_tls_initimage + main_map->l_addr;
- if (! main_map->l_map_end)
- main_map->l_map_end = ~0;
- if (! main_map->l_text_end)
- main_map->l_text_end = ~0;
- if (! GL(dl_rtld_map).l_libname && GL(dl_rtld_map).l_name)
- {
- /* We were invoked directly, so the program might not have a
- PT_INTERP. */
- _dl_rtld_libname.name = GL(dl_rtld_map).l_name;
- /* _dl_rtld_libname.next = NULL; Already zero. */
- GL(dl_rtld_map).l_libname = &_dl_rtld_libname;
- }
- else
- assert (GL(dl_rtld_map).l_libname); /* How else did we get here? */
-
- /* If the current libname is different from the SONAME, add the
- latter as well. */
- if (GL(dl_rtld_map).l_info[DT_SONAME] != NULL
- && strcmp (GL(dl_rtld_map).l_libname->name,
- (const char *) D_PTR (&GL(dl_rtld_map), l_info[DT_STRTAB])
- + GL(dl_rtld_map).l_info[DT_SONAME]->d_un.d_val) != 0)
- {
- static struct libname_list newname;
- newname.name = ((char *) D_PTR (&GL(dl_rtld_map), l_info[DT_STRTAB])
- + GL(dl_rtld_map).l_info[DT_SONAME]->d_un.d_ptr);
- newname.next = NULL;
- newname.dont_free = 1;
-
- assert (GL(dl_rtld_map).l_libname->next == NULL);
- GL(dl_rtld_map).l_libname->next = &newname;
- }
- /* The ld.so must be relocated since otherwise loading audit modules
- will fail since they reuse the very same ld.so. */
- assert (GL(dl_rtld_map).l_relocated);
-
- if (! rtld_is_main)
- {
- /* Extract the contents of the dynamic section for easy access. */
- elf_get_dynamic_info (main_map, NULL);
- /* Set up our cache of pointers into the hash table. */
- _dl_setup_hash (main_map);
- }
-
- if (__builtin_expect (mode, normal) == verify)
- {
- /* We were called just to verify that this is a dynamic
- executable using us as the program interpreter. Exit with an
- error if we were not able to load the binary or no interpreter
- is specified (i.e., this is no dynamically linked binary. */
- if (main_map->l_ld == NULL)
- _exit (1);
-
- /* We allow here some platform specific code. */
-#ifdef DISTINGUISH_LIB_VERSIONS
- DISTINGUISH_LIB_VERSIONS;
-#endif
- _exit (has_interp ? 0 : 2);
- }
-
- struct link_map **first_preload = &GL(dl_rtld_map).l_next;
- /* Set up the data structures for the system-supplied DSO early,
- so they can influence _dl_init_paths. */
- setup_vdso (main_map, &first_preload);
-
-#ifdef DL_SYSDEP_OSCHECK
- DL_SYSDEP_OSCHECK (_dl_fatal_printf);
-#endif
-
- /* Initialize the data structures for the search paths for shared
- objects. */
- _dl_init_paths (library_path);
-
- /* Initialize _r_debug. */
- struct r_debug *r = _dl_debug_initialize (GL(dl_rtld_map).l_addr,
- LM_ID_BASE);
- r->r_state = RT_CONSISTENT;
-
- /* Put the link_map for ourselves on the chain so it can be found by
- name. Note that at this point the global chain of link maps contains
- exactly one element, which is pointed to by dl_loaded. */
- if (! GL(dl_rtld_map).l_name)
- /* If not invoked directly, the dynamic linker shared object file was
- found by the PT_INTERP name. */
- GL(dl_rtld_map).l_name = (char *) GL(dl_rtld_map).l_libname->name;
- GL(dl_rtld_map).l_type = lt_library;
- main_map->l_next = &GL(dl_rtld_map);
- GL(dl_rtld_map).l_prev = main_map;
- ++GL(dl_ns)[LM_ID_BASE]._ns_nloaded;
- ++GL(dl_load_adds);
-
- /* If LD_USE_LOAD_BIAS env variable has not been seen, default
- to not using bias for non-prelinked PIEs and libraries
- and using it for executables or prelinked PIEs or libraries. */
- if (GLRO(dl_use_load_bias) == (ElfW(Addr)) -2)
- GLRO(dl_use_load_bias) = main_map->l_addr == 0 ? -1 : 0;
-
- /* Set up the program header information for the dynamic linker
- itself. It is needed in the dl_iterate_phdr callbacks. */
- const ElfW(Ehdr) *rtld_ehdr;
-
- /* Starting from binutils-2.23, the linker will define the magic symbol
- __ehdr_start to point to our own ELF header if it is visible in a
- segment that also includes the phdrs. If that's not available, we use
- the old method that assumes the beginning of the file is part of the
- lowest-addressed PT_LOAD segment. */
-#ifdef HAVE_EHDR_START
- extern const ElfW(Ehdr) __ehdr_start __attribute__ ((visibility ("hidden")));
- rtld_ehdr = &__ehdr_start;
-#else
- rtld_ehdr = (void *) GL(dl_rtld_map).l_map_start;
-#endif
- assert (rtld_ehdr->e_ehsize == sizeof *rtld_ehdr);
- assert (rtld_ehdr->e_phentsize == sizeof (ElfW(Phdr)));
-
- const ElfW(Phdr) *rtld_phdr = (const void *) rtld_ehdr + rtld_ehdr->e_phoff;
-
- GL(dl_rtld_map).l_phdr = rtld_phdr;
- GL(dl_rtld_map).l_phnum = rtld_ehdr->e_phnum;
-
-
- /* PT_GNU_RELRO is usually the last phdr. */
- size_t cnt = rtld_ehdr->e_phnum;
- while (cnt-- > 0)
- if (rtld_phdr[cnt].p_type == PT_GNU_RELRO)
- {
- GL(dl_rtld_map).l_relro_addr = rtld_phdr[cnt].p_vaddr;
- GL(dl_rtld_map).l_relro_size = rtld_phdr[cnt].p_memsz;
- break;
- }
-
- /* Add the dynamic linker to the TLS list if it also uses TLS. */
- if (GL(dl_rtld_map).l_tls_blocksize != 0)
- /* Assign a module ID. Do this before loading any audit modules. */
- GL(dl_rtld_map).l_tls_modid = _dl_next_tls_modid ();
-
- /* If we have auditing DSOs to load, do it now. */
- if (__glibc_unlikely (audit_list != NULL))
- {
- /* Iterate over all entries in the list. The order is important. */
- struct audit_ifaces *last_audit = NULL;
- struct audit_list *al = audit_list->next;
-
- /* Since we start using the auditing DSOs right away we need to
- initialize the data structures now. */
- tcbp = init_tls ();
-
- /* Initialize security features. We need to do it this early
- since otherwise the constructors of the audit libraries will
- use different values (especially the pointer guard) and will
- fail later on. */
- security_init ();
-
- do
- {
- int tls_idx = GL(dl_tls_max_dtv_idx);
-
- /* Now it is time to determine the layout of the static TLS
- block and allocate it for the initial thread. Note that we
- always allocate the static block, we never defer it even if
- no DF_STATIC_TLS bit is set. The reason is that we know
- glibc will use the static model. */
- struct dlmopen_args dlmargs;
- dlmargs.fname = al->name;
- dlmargs.map = NULL;
-
- const char *objname;
- const char *err_str = NULL;
- bool malloced;
- (void) _dl_catch_error (&objname, &err_str, &malloced, dlmopen_doit,
- &dlmargs);
- if (__glibc_unlikely (err_str != NULL))
- {
- not_loaded:
- _dl_error_printf ("\
-ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
- al->name, err_str);
- if (malloced)
- free ((char *) err_str);
- }
- else
- {
- struct lookup_args largs;
- largs.name = "la_version";
- largs.map = dlmargs.map;
-
- /* Check whether the interface version matches. */
- (void) _dl_catch_error (&objname, &err_str, &malloced,
- lookup_doit, &largs);
-
- unsigned int (*laversion) (unsigned int);
- unsigned int lav;
- if (err_str == NULL
- && (laversion = largs.result) != NULL
- && (lav = laversion (LAV_CURRENT)) > 0
- && lav <= LAV_CURRENT)
- {
- /* Allocate structure for the callback function pointers.
- This call can never fail. */
- union
- {
- struct audit_ifaces ifaces;
-#define naudit_ifaces 8
- void (*fptr[naudit_ifaces]) (void);
- } *newp = malloc (sizeof (*newp));
-
- /* Names of the auditing interfaces. All in one
- long string. */
- static const char audit_iface_names[] =
- "la_activity\0"
- "la_objsearch\0"
- "la_objopen\0"
- "la_preinit\0"
-#if __ELF_NATIVE_CLASS == 32
- "la_symbind32\0"
-#elif __ELF_NATIVE_CLASS == 64
- "la_symbind64\0"
-#else
-# error "__ELF_NATIVE_CLASS must be defined"
-#endif
-#define STRING(s) __STRING (s)
- "la_" STRING (ARCH_LA_PLTENTER) "\0"
- "la_" STRING (ARCH_LA_PLTEXIT) "\0"
- "la_objclose\0";
- unsigned int cnt = 0;
- const char *cp = audit_iface_names;
- do
- {
- largs.name = cp;
- (void) _dl_catch_error (&objname, &err_str, &malloced,
- lookup_doit, &largs);
-
- /* Store the pointer. */
- if (err_str == NULL && largs.result != NULL)
- {
- newp->fptr[cnt] = largs.result;
-
- /* The dynamic linker link map is statically
- allocated, initialize the data now. */
- GL(dl_rtld_map).l_audit[cnt].cookie
- = (intptr_t) &GL(dl_rtld_map);
- }
- else
- newp->fptr[cnt] = NULL;
- ++cnt;
-
- cp = (char *) rawmemchr (cp, '\0') + 1;
- }
- while (*cp != '\0');
- assert (cnt == naudit_ifaces);
-
- /* Now append the new auditing interface to the list. */
- newp->ifaces.next = NULL;
- if (last_audit == NULL)
- last_audit = GLRO(dl_audit) = &newp->ifaces;
- else
- last_audit = last_audit->next = &newp->ifaces;
- ++GLRO(dl_naudit);
-
- /* Mark the DSO as being used for auditing. */
- dlmargs.map->l_auditing = 1;
- }
- else
- {
- /* We cannot use the DSO, it does not have the
- appropriate interfaces or it expects something
- more recent. */
-#ifndef NDEBUG
- Lmid_t ns = dlmargs.map->l_ns;
-#endif
- _dl_close (dlmargs.map);
-
- /* Make sure the namespace has been cleared entirely. */
- assert (GL(dl_ns)[ns]._ns_loaded == NULL);
- assert (GL(dl_ns)[ns]._ns_nloaded == 0);
-
- GL(dl_tls_max_dtv_idx) = tls_idx;
- goto not_loaded;
- }
- }
-
- al = al->next;
- }
- while (al != audit_list->next);
-
- /* If we have any auditing modules, announce that we already
- have two objects loaded. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- struct link_map *ls[2] = { main_map, &GL(dl_rtld_map) };
-
- for (unsigned int outer = 0; outer < 2; ++outer)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->objopen != NULL)
- {
- ls[outer]->l_audit[cnt].bindflags
- = afct->objopen (ls[outer], LM_ID_BASE,
- &ls[outer]->l_audit[cnt].cookie);
-
- ls[outer]->l_audit_any_plt
- |= ls[outer]->l_audit[cnt].bindflags != 0;
- }
-
- afct = afct->next;
- }
- }
- }
- }
-
- /* Keep track of the currently loaded modules to count how many
- non-audit modules which use TLS are loaded. */
- size_t count_modids = _dl_count_modids ();
-
- /* Set up debugging before the debugger is notified for the first time. */
-#ifdef ELF_MACHINE_DEBUG_SETUP
- /* Some machines (e.g. MIPS) don't use DT_DEBUG in this way. */
- ELF_MACHINE_DEBUG_SETUP (main_map, r);
- ELF_MACHINE_DEBUG_SETUP (&GL(dl_rtld_map), r);
-#else
- if (main_map->l_info[DT_DEBUG] != NULL)
- /* There is a DT_DEBUG entry in the dynamic section. Fill it in
- with the run-time address of the r_debug structure */
- main_map->l_info[DT_DEBUG]->d_un.d_ptr = (ElfW(Addr)) r;
-
- /* Fill in the pointer in the dynamic linker's own dynamic section, in
- case you run gdb on the dynamic linker directly. */
- if (GL(dl_rtld_map).l_info[DT_DEBUG] != NULL)
- GL(dl_rtld_map).l_info[DT_DEBUG]->d_un.d_ptr = (ElfW(Addr)) r;
-#endif
-
- /* We start adding objects. */
- r->r_state = RT_ADD;
- _dl_debug_state ();
- LIBC_PROBE (init_start, 2, LM_ID_BASE, r);
-
- /* Auditing checkpoint: we are ready to signal that the initial map
- is being constructed. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&main_map->l_audit[cnt].cookie, LA_ACT_ADD);
-
- afct = afct->next;
- }
- }
-
- /* We have two ways to specify objects to preload: via environment
- variable and via the file /etc/ld.so.preload. The latter can also
- be used when security is enabled. */
- assert (*first_preload == NULL);
- struct link_map **preloads = NULL;
- unsigned int npreloads = 0;
-
- if (__glibc_unlikely (preloadlist != NULL))
- {
- /* The LD_PRELOAD environment variable gives list of libraries
- separated by white space or colons that are loaded before the
- executable's dependencies and prepended to the global scope
- list. If the binary is running setuid all elements
- containing a '/' are ignored since it is insecure. */
- char *list = strdupa (preloadlist);
- char *p;
-
- HP_TIMING_NOW (start);
-
- /* Prevent optimizing strsep. Speed is not important here. */
- while ((p = (strsep) (&list, " :")) != NULL)
- if (p[0] != '\0'
- && (__builtin_expect (! __libc_enable_secure, 1)
- || strchr (p, '/') == NULL))
- npreloads += do_preload (p, main_map, "LD_PRELOAD");
-
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (diff, start, stop);
- HP_TIMING_ACCUM_NT (load_time, diff);
- }
-
- /* There usually is no ld.so.preload file, it should only be used
- for emergencies and testing. So the open call etc should usually
- fail. Using access() on a non-existing file is faster than using
- open(). So we do this first. If it succeeds we do almost twice
- the work but this does not matter, since it is not for production
- use. */
- static const char preload_file[] = "/etc/ld.so.preload";
- if (__glibc_unlikely (__access (preload_file, R_OK) == 0))
- {
- /* Read the contents of the file. */
- file = _dl_sysdep_read_whole_file (preload_file, &file_size,
- PROT_READ | PROT_WRITE);
- if (__glibc_unlikely (file != MAP_FAILED))
- {
- /* Parse the file. It contains names of libraries to be loaded,
- separated by white spaces or `:'. It may also contain
- comments introduced by `#'. */
- char *problem;
- char *runp;
- size_t rest;
-
- /* Eliminate comments. */
- runp = file;
- rest = file_size;
- while (rest > 0)
- {
- char *comment = memchr (runp, '#', rest);
- if (comment == NULL)
- break;
-
- rest -= comment - runp;
- do
- *comment = ' ';
- while (--rest > 0 && *++comment != '\n');
- }
-
- /* We have one problematic case: if we have a name at the end of
- the file without a trailing terminating characters, we cannot
- place the \0. Handle the case separately. */
- if (file[file_size - 1] != ' ' && file[file_size - 1] != '\t'
- && file[file_size - 1] != '\n' && file[file_size - 1] != ':')
- {
- problem = &file[file_size];
- while (problem > file && problem[-1] != ' '
- && problem[-1] != '\t'
- && problem[-1] != '\n' && problem[-1] != ':')
- --problem;
-
- if (problem > file)
- problem[-1] = '\0';
- }
- else
- {
- problem = NULL;
- file[file_size - 1] = '\0';
- }
-
- HP_TIMING_NOW (start);
-
- if (file != problem)
- {
- char *p;
- runp = file;
- while ((p = strsep (&runp, ": \t\n")) != NULL)
- if (p[0] != '\0')
- npreloads += do_preload (p, main_map, preload_file);
- }
-
- if (problem != NULL)
- {
- char *p = strndupa (problem, file_size - (problem - file));
-
- npreloads += do_preload (p, main_map, preload_file);
- }
-
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (diff, start, stop);
- HP_TIMING_ACCUM_NT (load_time, diff);
-
- /* We don't need the file anymore. */
- __munmap (file, file_size);
- }
- }
-
- if (__glibc_unlikely (*first_preload != NULL))
- {
- /* Set up PRELOADS with a vector of the preloaded libraries. */
- struct link_map *l = *first_preload;
- preloads = __alloca (npreloads * sizeof preloads[0]);
- i = 0;
- do
- {
- preloads[i++] = l;
- l = l->l_next;
- } while (l);
- assert (i == npreloads);
- }
-
- /* Load all the libraries specified by DT_NEEDED entries. If LD_PRELOAD
- specified some libraries to load, these are inserted before the actual
- dependencies in the executable's searchlist for symbol resolution. */
- HP_TIMING_NOW (start);
- _dl_map_object_deps (main_map, preloads, npreloads, mode == trace, 0);
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (diff, start, stop);
- HP_TIMING_ACCUM_NT (load_time, diff);
-
- /* Mark all objects as being in the global scope. */
- for (i = main_map->l_searchlist.r_nlist; i > 0; )
- main_map->l_searchlist.r_list[--i]->l_global = 1;
-
- /* Remove _dl_rtld_map from the chain. */
- GL(dl_rtld_map).l_prev->l_next = GL(dl_rtld_map).l_next;
- if (GL(dl_rtld_map).l_next != NULL)
- GL(dl_rtld_map).l_next->l_prev = GL(dl_rtld_map).l_prev;
-
- for (i = 1; i < main_map->l_searchlist.r_nlist; ++i)
- if (main_map->l_searchlist.r_list[i] == &GL(dl_rtld_map))
- break;
-
- bool rtld_multiple_ref = false;
- if (__glibc_likely (i < main_map->l_searchlist.r_nlist))
- {
- /* Some DT_NEEDED entry referred to the interpreter object itself, so
- put it back in the list of visible objects. We insert it into the
- chain in symbol search order because gdb uses the chain's order as
- its symbol search order. */
- rtld_multiple_ref = true;
-
- GL(dl_rtld_map).l_prev = main_map->l_searchlist.r_list[i - 1];
- if (__builtin_expect (mode, normal) == normal)
- {
- GL(dl_rtld_map).l_next = (i + 1 < main_map->l_searchlist.r_nlist
- ? main_map->l_searchlist.r_list[i + 1]
- : NULL);
-#ifdef NEED_DL_SYSINFO_DSO
- if (GLRO(dl_sysinfo_map) != NULL
- && GL(dl_rtld_map).l_prev->l_next == GLRO(dl_sysinfo_map)
- && GL(dl_rtld_map).l_next != GLRO(dl_sysinfo_map))
- GL(dl_rtld_map).l_prev = GLRO(dl_sysinfo_map);
-#endif
- }
- else
- /* In trace mode there might be an invisible object (which we
- could not find) after the previous one in the search list.
- In this case it doesn't matter much where we put the
- interpreter object, so we just initialize the list pointer so
- that the assertion below holds. */
- GL(dl_rtld_map).l_next = GL(dl_rtld_map).l_prev->l_next;
-
- assert (GL(dl_rtld_map).l_prev->l_next == GL(dl_rtld_map).l_next);
- GL(dl_rtld_map).l_prev->l_next = &GL(dl_rtld_map);
- if (GL(dl_rtld_map).l_next != NULL)
- {
- assert (GL(dl_rtld_map).l_next->l_prev == GL(dl_rtld_map).l_prev);
- GL(dl_rtld_map).l_next->l_prev = &GL(dl_rtld_map);
- }
- }
-
- /* Now let us see whether all libraries are available in the
- versions we need. */
- {
- struct version_check_args args;
- args.doexit = mode == normal;
- args.dotrace = mode == trace;
- _dl_receive_error (print_missing_version, version_check_doit, &args);
- }
-
- /* We do not initialize any of the TLS functionality unless any of the
- initial modules uses TLS. This makes dynamic loading of modules with
- TLS impossible, but to support it requires either eagerly doing setup
- now or lazily doing it later. Doing it now makes us incompatible with
- an old kernel that can't perform TLS_INIT_TP, even if no TLS is ever
- used. Trying to do it lazily is too hairy to try when there could be
- multiple threads (from a non-TLS-using libpthread). */
- bool was_tls_init_tp_called = tls_init_tp_called;
- if (tcbp == NULL)
- tcbp = init_tls ();
-
- if (__glibc_likely (audit_list == NULL))
- /* Initialize security features. But only if we have not done it
- earlier. */
- security_init ();
-
- if (__builtin_expect (mode, normal) != normal)
- {
- /* We were run just to list the shared libraries. It is
- important that we do this before real relocation, because the
- functions we call below for output may no longer work properly
- after relocation. */
- struct link_map *l;
-
- if (GLRO(dl_debug_mask) & DL_DEBUG_PRELINK)
- {
- struct r_scope_elem *scope = &main_map->l_searchlist;
-
- for (i = 0; i < scope->r_nlist; i++)
- {
- l = scope->r_list [i];
- if (l->l_faked)
- {
- _dl_printf ("\t%s => not found\n", l->l_libname->name);
- continue;
- }
- if (_dl_name_match_p (GLRO(dl_trace_prelink), l))
- GLRO(dl_trace_prelink_map) = l;
- _dl_printf ("\t%s => %s (0x%0*Zx, 0x%0*Zx)",
- DSO_FILENAME (l->l_libname->name),
- DSO_FILENAME (l->l_name),
- (int) sizeof l->l_map_start * 2,
- (size_t) l->l_map_start,
- (int) sizeof l->l_addr * 2,
- (size_t) l->l_addr);
-
- if (l->l_tls_modid)
- _dl_printf (" TLS(0x%Zx, 0x%0*Zx)\n", l->l_tls_modid,
- (int) sizeof l->l_tls_offset * 2,
- (size_t) l->l_tls_offset);
- else
- _dl_printf ("\n");
- }
- }
- else if (GLRO(dl_debug_mask) & DL_DEBUG_UNUSED)
- {
- /* Look through the dependencies of the main executable
- and determine which of them is not actually
- required. */
- struct link_map *l = main_map;
-
- /* Relocate the main executable. */
- struct relocate_args args = { .l = l,
- .reloc_mode = ((GLRO(dl_lazy)
- ? RTLD_LAZY : 0)
- | __RTLD_NOIFUNC) };
- _dl_receive_error (print_unresolved, relocate_doit, &args);
-
- /* This loop depends on the dependencies of the executable to
- correspond in number and order to the DT_NEEDED entries. */
- ElfW(Dyn) *dyn = main_map->l_ld;
- bool first = true;
- while (dyn->d_tag != DT_NULL)
- {
- if (dyn->d_tag == DT_NEEDED)
- {
- l = l->l_next;
-#ifdef NEED_DL_SYSINFO_DSO
- /* Skip the VDSO since it's not part of the list
- of objects we brought in via DT_NEEDED entries. */
- if (l == GLRO(dl_sysinfo_map))
- l = l->l_next;
-#endif
- if (!l->l_used)
- {
- if (first)
- {
- _dl_printf ("Unused direct dependencies:\n");
- first = false;
- }
-
- _dl_printf ("\t%s\n", l->l_name);
- }
- }
-
- ++dyn;
- }
-
- _exit (first != true);
- }
- else if (! main_map->l_info[DT_NEEDED])
- _dl_printf ("\tstatically linked\n");
- else
- {
- for (l = main_map->l_next; l; l = l->l_next)
- if (l->l_faked)
- /* The library was not found. */
- _dl_printf ("\t%s => not found\n", l->l_libname->name);
- else if (strcmp (l->l_libname->name, l->l_name) == 0)
- _dl_printf ("\t%s (0x%0*Zx)\n", l->l_libname->name,
- (int) sizeof l->l_map_start * 2,
- (size_t) l->l_map_start);
- else
- _dl_printf ("\t%s => %s (0x%0*Zx)\n", l->l_libname->name,
- l->l_name, (int) sizeof l->l_map_start * 2,
- (size_t) l->l_map_start);
- }
-
- if (__builtin_expect (mode, trace) != trace)
- for (i = 1; i < (unsigned int) _dl_argc; ++i)
- {
- const ElfW(Sym) *ref = NULL;
- ElfW(Addr) loadbase;
- lookup_t result;
-
- result = _dl_lookup_symbol_x (_dl_argv[i], main_map,
- &ref, main_map->l_scope,
- NULL, ELF_RTYPE_CLASS_PLT,
- DL_LOOKUP_ADD_DEPENDENCY, NULL);
-
- loadbase = LOOKUP_VALUE_ADDRESS (result);
-
- _dl_printf ("%s found at 0x%0*Zd in object at 0x%0*Zd\n",
- _dl_argv[i],
- (int) sizeof ref->st_value * 2,
- (size_t) ref->st_value,
- (int) sizeof loadbase * 2, (size_t) loadbase);
- }
- else
- {
- /* If LD_WARN is set, warn about undefined symbols. */
- if (GLRO(dl_lazy) >= 0 && GLRO(dl_verbose))
- {
- /* We have to do symbol dependency testing. */
- struct relocate_args args;
- unsigned int i;
-
- args.reloc_mode = ((GLRO(dl_lazy) ? RTLD_LAZY : 0)
- | __RTLD_NOIFUNC);
-
- i = main_map->l_searchlist.r_nlist;
- while (i-- > 0)
- {
- struct link_map *l = main_map->l_initfini[i];
- if (l != &GL(dl_rtld_map) && ! l->l_faked)
- {
- args.l = l;
- _dl_receive_error (print_unresolved, relocate_doit,
- &args);
- }
- }
-
- if ((GLRO(dl_debug_mask) & DL_DEBUG_PRELINK)
- && rtld_multiple_ref)
- {
- /* Mark the link map as not yet relocated again. */
- GL(dl_rtld_map).l_relocated = 0;
- _dl_relocate_object (&GL(dl_rtld_map),
- main_map->l_scope, __RTLD_NOIFUNC, 0);
- }
- }
-#define VERNEEDTAG (DT_NUM + DT_THISPROCNUM + DT_VERSIONTAGIDX (DT_VERNEED))
- if (version_info)
- {
- /* Print more information. This means here, print information
- about the versions needed. */
- int first = 1;
- struct link_map *map;
-
- for (map = main_map; map != NULL; map = map->l_next)
- {
- const char *strtab;
- ElfW(Dyn) *dyn = map->l_info[VERNEEDTAG];
- ElfW(Verneed) *ent;
-
- if (dyn == NULL)
- continue;
-
- strtab = (const void *) D_PTR (map, l_info[DT_STRTAB]);
- ent = (ElfW(Verneed) *) (map->l_addr + dyn->d_un.d_ptr);
-
- if (first)
- {
- _dl_printf ("\n\tVersion information:\n");
- first = 0;
- }
-
- _dl_printf ("\t%s:\n", DSO_FILENAME (map->l_name));
-
- while (1)
- {
- ElfW(Vernaux) *aux;
- struct link_map *needed;
-
- needed = find_needed (strtab + ent->vn_file);
- aux = (ElfW(Vernaux) *) ((char *) ent + ent->vn_aux);
-
- while (1)
- {
- const char *fname = NULL;
-
- if (needed != NULL
- && match_version (strtab + aux->vna_name,
- needed))
- fname = needed->l_name;
-
- _dl_printf ("\t\t%s (%s) %s=> %s\n",
- strtab + ent->vn_file,
- strtab + aux->vna_name,
- aux->vna_flags & VER_FLG_WEAK
- ? "[WEAK] " : "",
- fname ?: "not found");
-
- if (aux->vna_next == 0)
- /* No more symbols. */
- break;
-
- /* Next symbol. */
- aux = (ElfW(Vernaux) *) ((char *) aux
- + aux->vna_next);
- }
-
- if (ent->vn_next == 0)
- /* No more dependencies. */
- break;
-
- /* Next dependency. */
- ent = (ElfW(Verneed) *) ((char *) ent + ent->vn_next);
- }
- }
- }
- }
-
- _exit (0);
- }
-
- if (main_map->l_info[ADDRIDX (DT_GNU_LIBLIST)]
- && ! __builtin_expect (GLRO(dl_profile) != NULL, 0)
- && ! __builtin_expect (GLRO(dl_dynamic_weak), 0))
- {
- ElfW(Lib) *liblist, *liblistend;
- struct link_map **r_list, **r_listend, *l;
- const char *strtab = (const void *) D_PTR (main_map, l_info[DT_STRTAB]);
-
- assert (main_map->l_info[VALIDX (DT_GNU_LIBLISTSZ)] != NULL);
- liblist = (ElfW(Lib) *)
- main_map->l_info[ADDRIDX (DT_GNU_LIBLIST)]->d_un.d_ptr;
- liblistend = (ElfW(Lib) *)
- ((char *) liblist +
- main_map->l_info[VALIDX (DT_GNU_LIBLISTSZ)]->d_un.d_val);
- r_list = main_map->l_searchlist.r_list;
- r_listend = r_list + main_map->l_searchlist.r_nlist;
-
- for (; r_list < r_listend && liblist < liblistend; r_list++)
- {
- l = *r_list;
-
- if (l == main_map)
- continue;
-
- /* If the library is not mapped where it should, fail. */
- if (l->l_addr)
- break;
-
- /* Next, check if checksum matches. */
- if (l->l_info [VALIDX(DT_CHECKSUM)] == NULL
- || l->l_info [VALIDX(DT_CHECKSUM)]->d_un.d_val
- != liblist->l_checksum)
- break;
-
- if (l->l_info [VALIDX(DT_GNU_PRELINKED)] == NULL
- || l->l_info [VALIDX(DT_GNU_PRELINKED)]->d_un.d_val
- != liblist->l_time_stamp)
- break;
-
- if (! _dl_name_match_p (strtab + liblist->l_name, l))
- break;
-
- ++liblist;
- }
-
-
- if (r_list == r_listend && liblist == liblistend)
- prelinked = true;
-
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_LIBS))
- _dl_debug_printf ("\nprelink checking: %s\n",
- prelinked ? "ok" : "failed");
- }
-
-
- /* Now set up the variable which helps the assembler startup code. */
- GL(dl_ns)[LM_ID_BASE]._ns_main_searchlist = &main_map->l_searchlist;
-
- /* Save the information about the original global scope list since
- we need it in the memory handling later. */
- GLRO(dl_initial_searchlist) = *GL(dl_ns)[LM_ID_BASE]._ns_main_searchlist;
-
- /* Remember the last search directory added at startup, now that
- malloc will no longer be the one from dl-minimal.c. */
- GLRO(dl_init_all_dirs) = GL(dl_all_dirs);
-
- /* Print scope information. */
- if (__glibc_unlikely (GLRO(dl_debug_mask) & DL_DEBUG_SCOPES))
- {
- _dl_debug_printf ("\nInitial object scopes\n");
-
- for (struct link_map *l = main_map; l != NULL; l = l->l_next)
- _dl_show_scope (l, 0);
- }
-
- if (prelinked)
- {
- if (main_map->l_info [ADDRIDX (DT_GNU_CONFLICT)] != NULL)
- {
- ElfW(Rela) *conflict, *conflictend;
-#ifndef HP_TIMING_NONAVAIL
- hp_timing_t start;
- hp_timing_t stop;
-#endif
-
- HP_TIMING_NOW (start);
- assert (main_map->l_info [VALIDX (DT_GNU_CONFLICTSZ)] != NULL);
- conflict = (ElfW(Rela) *)
- main_map->l_info [ADDRIDX (DT_GNU_CONFLICT)]->d_un.d_ptr;
- conflictend = (ElfW(Rela) *)
- ((char *) conflict
- + main_map->l_info [VALIDX (DT_GNU_CONFLICTSZ)]->d_un.d_val);
- _dl_resolve_conflicts (main_map, conflict, conflictend);
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (relocate_time, start, stop);
- }
-
-
- /* Mark all the objects so we know they have been already relocated. */
- for (struct link_map *l = main_map; l != NULL; l = l->l_next)
- {
- l->l_relocated = 1;
- if (l->l_relro_size)
- _dl_protect_relro (l);
-
- /* Add object to slot information data if necessasy. */
- if (l->l_tls_blocksize != 0 && tls_init_tp_called)
- _dl_add_to_slotinfo (l);
- }
- }
- else
- {
- /* Now we have all the objects loaded. Relocate them all except for
- the dynamic linker itself. We do this in reverse order so that copy
- relocs of earlier objects overwrite the data written by later
- objects. We do not re-relocate the dynamic linker itself in this
- loop because that could result in the GOT entries for functions we
- call being changed, and that would break us. It is safe to relocate
- the dynamic linker out of order because it has no copy relocs (we
- know that because it is self-contained). */
-
- int consider_profiling = GLRO(dl_profile) != NULL;
-#ifndef HP_TIMING_NONAVAIL
- hp_timing_t start;
- hp_timing_t stop;
-#endif
-
- /* If we are profiling we also must do lazy reloaction. */
- GLRO(dl_lazy) |= consider_profiling;
-
- HP_TIMING_NOW (start);
- unsigned i = main_map->l_searchlist.r_nlist;
- while (i-- > 0)
- {
- struct link_map *l = main_map->l_initfini[i];
-
- /* While we are at it, help the memory handling a bit. We have to
- mark some data structures as allocated with the fake malloc()
- implementation in ld.so. */
- struct libname_list *lnp = l->l_libname->next;
-
- while (__builtin_expect (lnp != NULL, 0))
- {
- lnp->dont_free = 1;
- lnp = lnp->next;
- }
- /* Also allocated with the fake malloc(). */
- l->l_free_initfini = 0;
-
- if (l != &GL(dl_rtld_map))
- _dl_relocate_object (l, l->l_scope, GLRO(dl_lazy) ? RTLD_LAZY : 0,
- consider_profiling);
-
- /* Add object to slot information data if necessasy. */
- if (l->l_tls_blocksize != 0 && tls_init_tp_called)
- _dl_add_to_slotinfo (l);
- }
- HP_TIMING_NOW (stop);
-
- HP_TIMING_DIFF (relocate_time, start, stop);
-
- /* Now enable profiling if needed. Like the previous call,
- this has to go here because the calls it makes should use the
- rtld versions of the functions (particularly calloc()), but it
- needs to have _dl_profile_map set up by the relocator. */
- if (__glibc_unlikely (GL(dl_profile_map) != NULL))
- /* We must prepare the profiling. */
- _dl_start_profile ();
- }
-
- if ((!was_tls_init_tp_called && GL(dl_tls_max_dtv_idx) > 0)
- || count_modids != _dl_count_modids ())
- ++GL(dl_tls_generation);
-
- /* Now that we have completed relocation, the initializer data
- for the TLS blocks has its final values and we can copy them
- into the main thread's TLS area, which we allocated above. */
- _dl_allocate_tls_init (tcbp);
-
- /* And finally install it for the main thread. */
- if (! tls_init_tp_called)
- {
- const char *lossage = TLS_INIT_TP (tcbp);
- if (__glibc_unlikely (lossage != NULL))
- _dl_fatal_printf ("cannot set up thread-local storage: %s\n",
- lossage);
- }
-
- /* Make sure no new search directories have been added. */
- assert (GLRO(dl_init_all_dirs) == GL(dl_all_dirs));
-
- if (! prelinked && rtld_multiple_ref)
- {
- /* There was an explicit ref to the dynamic linker as a shared lib.
- Re-relocate ourselves with user-controlled symbol definitions.
-
- We must do this after TLS initialization in case after this
- re-relocation, we might call a user-supplied function
- (e.g. calloc from _dl_relocate_object) that uses TLS data. */
-
-#ifndef HP_TIMING_NONAVAIL
- hp_timing_t start;
- hp_timing_t stop;
- hp_timing_t add;
-#endif
-
- HP_TIMING_NOW (start);
- /* Mark the link map as not yet relocated again. */
- GL(dl_rtld_map).l_relocated = 0;
- _dl_relocate_object (&GL(dl_rtld_map), main_map->l_scope, 0, 0);
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (add, start, stop);
- HP_TIMING_ACCUM_NT (relocate_time, add);
- }
-
- /* Do any necessary cleanups for the startup OS interface code.
- We do these now so that no calls are made after rtld re-relocation
- which might be resolved to different functions than we expect.
- We cannot do this before relocating the other objects because
- _dl_relocate_object might need to call `mprotect' for DT_TEXTREL. */
- _dl_sysdep_start_cleanup ();
-
-#ifdef SHARED
- /* Auditing checkpoint: we have added all objects. */
- if (__glibc_unlikely (GLRO(dl_naudit) > 0))
- {
- struct link_map *head = GL(dl_ns)[LM_ID_BASE]._ns_loaded;
- /* Do not call the functions for any auditing object. */
- if (head->l_auditing == 0)
- {
- struct audit_ifaces *afct = GLRO(dl_audit);
- for (unsigned int cnt = 0; cnt < GLRO(dl_naudit); ++cnt)
- {
- if (afct->activity != NULL)
- afct->activity (&head->l_audit[cnt].cookie, LA_ACT_CONSISTENT);
-
- afct = afct->next;
- }
- }
- }
-#endif
-
- /* Notify the debugger all new objects are now ready to go. We must re-get
- the address since by now the variable might be in another object. */
- r = _dl_debug_initialize (0, LM_ID_BASE);
- r->r_state = RT_CONSISTENT;
- _dl_debug_state ();
- LIBC_PROBE (init_complete, 2, LM_ID_BASE, r);
-
-#if defined USE_LDCONFIG && !defined MAP_COPY
- /* We must munmap() the cache file. */
- _dl_unload_cache ();
-#endif
-
- /* Once we return, _dl_sysdep_start will invoke
- the DT_INIT functions and then *USER_ENTRY. */
-}
-
-/* This is a little helper function for resolving symbols while
- tracing the binary. */
-static void
-print_unresolved (int errcode __attribute__ ((unused)), const char *objname,
- const char *errstring)
-{
- if (objname[0] == '\0')
- objname = RTLD_PROGNAME;
- _dl_error_printf ("%s (%s)\n", errstring, objname);
-}
-
-/* This is a little helper function for resolving symbols while
- tracing the binary. */
-static void
-print_missing_version (int errcode __attribute__ ((unused)),
- const char *objname, const char *errstring)
-{
- _dl_error_printf ("%s: %s: %s\n", RTLD_PROGNAME,
- objname, errstring);
-}
-
-/* Nonzero if any of the debugging options is enabled. */
-static int any_debug attribute_relro;
-
-/* Process the string given as the parameter which explains which debugging
- options are enabled. */
-static void
-process_dl_debug (const char *dl_debug)
-{
- /* When adding new entries make sure that the maximal length of a name
- is correctly handled in the LD_DEBUG_HELP code below. */
- static const struct
- {
- unsigned char len;
- const char name[10];
- const char helptext[41];
- unsigned short int mask;
- } debopts[] =
- {
-#define LEN_AND_STR(str) sizeof (str) - 1, str
- { LEN_AND_STR ("libs"), "display library search paths",
- DL_DEBUG_LIBS | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("reloc"), "display relocation processing",
- DL_DEBUG_RELOC | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("files"), "display progress for input file",
- DL_DEBUG_FILES | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("symbols"), "display symbol table processing",
- DL_DEBUG_SYMBOLS | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("bindings"), "display information about symbol binding",
- DL_DEBUG_BINDINGS | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("versions"), "display version dependencies",
- DL_DEBUG_VERSIONS | DL_DEBUG_IMPCALLS },
- { LEN_AND_STR ("scopes"), "display scope information",
- DL_DEBUG_SCOPES },
- { LEN_AND_STR ("all"), "all previous options combined",
- DL_DEBUG_LIBS | DL_DEBUG_RELOC | DL_DEBUG_FILES | DL_DEBUG_SYMBOLS
- | DL_DEBUG_BINDINGS | DL_DEBUG_VERSIONS | DL_DEBUG_IMPCALLS
- | DL_DEBUG_SCOPES },
- { LEN_AND_STR ("statistics"), "display relocation statistics",
- DL_DEBUG_STATISTICS },
- { LEN_AND_STR ("unused"), "determined unused DSOs",
- DL_DEBUG_UNUSED },
- { LEN_AND_STR ("help"), "display this help message and exit",
- DL_DEBUG_HELP },
- };
-#define ndebopts (sizeof (debopts) / sizeof (debopts[0]))
-
- /* Skip separating white spaces and commas. */
- while (*dl_debug != '\0')
- {
- if (*dl_debug != ' ' && *dl_debug != ',' && *dl_debug != ':')
- {
- size_t cnt;
- size_t len = 1;
-
- while (dl_debug[len] != '\0' && dl_debug[len] != ' '
- && dl_debug[len] != ',' && dl_debug[len] != ':')
- ++len;
-
- for (cnt = 0; cnt < ndebopts; ++cnt)
- if (debopts[cnt].len == len
- && memcmp (dl_debug, debopts[cnt].name, len) == 0)
- {
- GLRO(dl_debug_mask) |= debopts[cnt].mask;
- any_debug = 1;
- break;
- }
-
- if (cnt == ndebopts)
- {
- /* Display a warning and skip everything until next
- separator. */
- char *copy = strndupa (dl_debug, len);
- _dl_error_printf ("\
-warning: debug option `%s' unknown; try LD_DEBUG=help\n", copy);
- }
-
- dl_debug += len;
- continue;
- }
-
- ++dl_debug;
- }
-
- if (GLRO(dl_debug_mask) & DL_DEBUG_UNUSED)
- {
- /* In order to get an accurate picture of whether a particular
- DT_NEEDED entry is actually used we have to process both
- the PLT and non-PLT relocation entries. */
- GLRO(dl_lazy) = 0;
- }
-
- if (GLRO(dl_debug_mask) & DL_DEBUG_HELP)
- {
- size_t cnt;
-
- _dl_printf ("\
-Valid options for the LD_DEBUG environment variable are:\n\n");
-
- for (cnt = 0; cnt < ndebopts; ++cnt)
- _dl_printf (" %.*s%s%s\n", debopts[cnt].len, debopts[cnt].name,
- " " + debopts[cnt].len - 3,
- debopts[cnt].helptext);
-
- _dl_printf ("\n\
-To direct the debugging output into a file instead of standard output\n\
-a filename can be specified using the LD_DEBUG_OUTPUT environment variable.\n");
- _exit (0);
- }
-}
-
-static void
-process_dl_audit (char *str)
-{
- /* The parameter is a colon separated list of DSO names. */
- char *p;
-
- while ((p = (strsep) (&str, ":")) != NULL)
- if (p[0] != '\0'
- && (__builtin_expect (! __libc_enable_secure, 1)
- || strchr (p, '/') == NULL))
- {
- /* This is using the local malloc, not the system malloc. The
- memory can never be freed. */
- struct audit_list *newp = malloc (sizeof (*newp));
- newp->name = p;
-
- if (audit_list == NULL)
- audit_list = newp->next = newp;
- else
- {
- newp->next = audit_list->next;
- audit_list = audit_list->next = newp;
- }
- }
-}
-
-/* Process all environments variables the dynamic linker must recognize.
- Since all of them start with `LD_' we are a bit smarter while finding
- all the entries. */
-extern char **_environ attribute_hidden;
-
-
-static void
-process_envvars (enum mode *modep)
-{
- char **runp = _environ;
- char *envline;
- enum mode mode = normal;
- char *debug_output = NULL;
-
- /* This is the default place for profiling data file. */
- GLRO(dl_profile_output)
- = &"/var/tmp\0/var/profile"[__libc_enable_secure ? 9 : 0];
-
- while ((envline = _dl_next_ld_env_entry (&runp)) != NULL)
- {
- size_t len = 0;
-
- while (envline[len] != '\0' && envline[len] != '=')
- ++len;
-
- if (envline[len] != '=')
- /* This is a "LD_" variable at the end of the string without
- a '=' character. Ignore it since otherwise we will access
- invalid memory below. */
- continue;
-
- switch (len)
- {
- case 4:
- /* Warning level, verbose or not. */
- if (memcmp (envline, "WARN", 4) == 0)
- GLRO(dl_verbose) = envline[5] != '\0';
- break;
-
- case 5:
- /* Debugging of the dynamic linker? */
- if (memcmp (envline, "DEBUG", 5) == 0)
- {
- process_dl_debug (&envline[6]);
- break;
- }
- if (memcmp (envline, "AUDIT", 5) == 0)
- process_dl_audit (&envline[6]);
- break;
-
- case 7:
- /* Print information about versions. */
- if (memcmp (envline, "VERBOSE", 7) == 0)
- {
- version_info = envline[8] != '\0';
- break;
- }
-
- /* List of objects to be preloaded. */
- if (memcmp (envline, "PRELOAD", 7) == 0)
- {
- preloadlist = &envline[8];
- break;
- }
-
- /* Which shared object shall be profiled. */
- if (memcmp (envline, "PROFILE", 7) == 0 && envline[8] != '\0')
- GLRO(dl_profile) = &envline[8];
- break;
-
- case 8:
- /* Do we bind early? */
- if (memcmp (envline, "BIND_NOW", 8) == 0)
- {
- GLRO(dl_lazy) = envline[9] == '\0';
- break;
- }
- if (memcmp (envline, "BIND_NOT", 8) == 0)
- GLRO(dl_bind_not) = envline[9] != '\0';
- break;
-
- case 9:
- /* Test whether we want to see the content of the auxiliary
- array passed up from the kernel. */
- if (!__libc_enable_secure
- && memcmp (envline, "SHOW_AUXV", 9) == 0)
- _dl_show_auxv ();
- break;
-
-#if !HAVE_TUNABLES
- case 10:
- /* Mask for the important hardware capabilities. */
- if (!__libc_enable_secure
- && memcmp (envline, "HWCAP_MASK", 10) == 0)
- GLRO(dl_hwcap_mask) = __strtoul_internal (&envline[11], NULL,
- 0, 0);
- break;
-#endif
-
- case 11:
- /* Path where the binary is found. */
- if (!__libc_enable_secure
- && memcmp (envline, "ORIGIN_PATH", 11) == 0)
- GLRO(dl_origin_path) = &envline[12];
- break;
-
- case 12:
- /* The library search path. */
- if (memcmp (envline, "LIBRARY_PATH", 12) == 0)
- {
- library_path = &envline[13];
- break;
- }
-
- /* Where to place the profiling data file. */
- if (memcmp (envline, "DEBUG_OUTPUT", 12) == 0)
- {
- debug_output = &envline[13];
- break;
- }
-
- if (!__libc_enable_secure
- && memcmp (envline, "DYNAMIC_WEAK", 12) == 0)
- GLRO(dl_dynamic_weak) = 1;
- break;
-
- case 13:
- /* We might have some extra environment variable with length 13
- to handle. */
-#ifdef EXTRA_LD_ENVVARS_13
- EXTRA_LD_ENVVARS_13
-#endif
- if (!__libc_enable_secure
- && memcmp (envline, "USE_LOAD_BIAS", 13) == 0)
- {
- GLRO(dl_use_load_bias) = envline[14] == '1' ? -1 : 0;
- break;
- }
- break;
-
- case 14:
- /* Where to place the profiling data file. */
- if (!__libc_enable_secure
- && memcmp (envline, "PROFILE_OUTPUT", 14) == 0
- && envline[15] != '\0')
- GLRO(dl_profile_output) = &envline[15];
- break;
-
- case 16:
- /* The mode of the dynamic linker can be set. */
- if (memcmp (envline, "TRACE_PRELINKING", 16) == 0)
- {
- mode = trace;
- GLRO(dl_verbose) = 1;
- GLRO(dl_debug_mask) |= DL_DEBUG_PRELINK;
- GLRO(dl_trace_prelink) = &envline[17];
- }
- break;
-
- case 20:
- /* The mode of the dynamic linker can be set. */
- if (memcmp (envline, "TRACE_LOADED_OBJECTS", 20) == 0)
- mode = trace;
- break;
-
- /* We might have some extra environment variable to handle. This
- is tricky due to the pre-processing of the length of the name
- in the switch statement here. The code here assumes that added
- environment variables have a different length. */
-#ifdef EXTRA_LD_ENVVARS
- EXTRA_LD_ENVVARS
-#endif
- }
- }
-
- /* The caller wants this information. */
- *modep = mode;
-
- /* Extra security for SUID binaries. Remove all dangerous environment
- variables. */
- if (__builtin_expect (__libc_enable_secure, 0))
- {
- static const char unsecure_envvars[] =
-#ifdef EXTRA_UNSECURE_ENVVARS
- EXTRA_UNSECURE_ENVVARS
-#endif
- UNSECURE_ENVVARS;
- const char *nextp;
-
- nextp = unsecure_envvars;
- do
- {
- unsetenv (nextp);
- /* We could use rawmemchr but this need not be fast. */
- nextp = (char *) (strchr) (nextp, '\0') + 1;
- }
- while (*nextp != '\0');
-
- if (__access ("/etc/suid-debug", F_OK) != 0)
- {
-#if !HAVE_TUNABLES
- unsetenv ("MALLOC_CHECK_");
-#endif
- GLRO(dl_debug_mask) = 0;
- }
-
- if (mode != normal)
- _exit (5);
- }
- /* If we have to run the dynamic linker in debugging mode and the
- LD_DEBUG_OUTPUT environment variable is given, we write the debug
- messages to this file. */
- else if (any_debug && debug_output != NULL)
- {
- const int flags = O_WRONLY | O_APPEND | O_CREAT | O_NOFOLLOW;
- size_t name_len = strlen (debug_output);
- char buf[name_len + 12];
- char *startp;
-
- buf[name_len + 11] = '\0';
- startp = _itoa (__getpid (), &buf[name_len + 11], 10, 0);
- *--startp = '.';
- startp = memcpy (startp - name_len, debug_output, name_len);
-
- GLRO(dl_debug_fd) = __open (startp, flags, DEFFILEMODE);
- if (GLRO(dl_debug_fd) == -1)
- /* We use standard output if opening the file failed. */
- GLRO(dl_debug_fd) = STDOUT_FILENO;
- }
-}
-
-
-/* Print the various times we collected. */
-static void
-__attribute ((noinline))
-print_statistics (hp_timing_t *rtld_total_timep)
-{
-#ifndef HP_TIMING_NONAVAIL
- char buf[200];
- char *cp;
- char *wp;
-
- /* Total time rtld used. */
- if (HP_SMALL_TIMING_AVAIL)
- {
- HP_TIMING_PRINT (buf, sizeof (buf), *rtld_total_timep);
- _dl_debug_printf ("\nruntime linker statistics:\n"
- " total startup time in dynamic loader: %s\n", buf);
-
- /* Print relocation statistics. */
- char pbuf[30];
- HP_TIMING_PRINT (buf, sizeof (buf), relocate_time);
- cp = _itoa ((1000ULL * relocate_time) / *rtld_total_timep,
- pbuf + sizeof (pbuf), 10, 0);
- wp = pbuf;
- switch (pbuf + sizeof (pbuf) - cp)
- {
- case 3:
- *wp++ = *cp++;
- case 2:
- *wp++ = *cp++;
- case 1:
- *wp++ = '.';
- *wp++ = *cp++;
- }
- *wp = '\0';
- _dl_debug_printf ("\
- time needed for relocation: %s (%s%%)\n", buf, pbuf);
- }
-#endif
-
- unsigned long int num_relative_relocations = 0;
- for (Lmid_t ns = 0; ns < GL(dl_nns); ++ns)
- {
- if (GL(dl_ns)[ns]._ns_loaded == NULL)
- continue;
-
- struct r_scope_elem *scope = &GL(dl_ns)[ns]._ns_loaded->l_searchlist;
-
- for (unsigned int i = 0; i < scope->r_nlist; i++)
- {
- struct link_map *l = scope->r_list [i];
-
- if (l->l_addr != 0 && l->l_info[VERSYMIDX (DT_RELCOUNT)])
- num_relative_relocations
- += l->l_info[VERSYMIDX (DT_RELCOUNT)]->d_un.d_val;
-#ifndef ELF_MACHINE_REL_RELATIVE
- /* Relative relocations are processed on these architectures if
- library is loaded to different address than p_vaddr or
- if not prelinked. */
- if ((l->l_addr != 0 || !l->l_info[VALIDX(DT_GNU_PRELINKED)])
- && l->l_info[VERSYMIDX (DT_RELACOUNT)])
-#else
- /* On e.g. IA-64 or Alpha, relative relocations are processed
- only if library is loaded to different address than p_vaddr. */
- if (l->l_addr != 0 && l->l_info[VERSYMIDX (DT_RELACOUNT)])
-#endif
- num_relative_relocations
- += l->l_info[VERSYMIDX (DT_RELACOUNT)]->d_un.d_val;
- }
- }
-
- _dl_debug_printf (" number of relocations: %lu\n"
- " number of relocations from cache: %lu\n"
- " number of relative relocations: %lu\n",
- GL(dl_num_relocations),
- GL(dl_num_cache_relocations),
- num_relative_relocations);
-
-#ifndef HP_TIMING_NONAVAIL
- /* Time spend while loading the object and the dependencies. */
- if (HP_SMALL_TIMING_AVAIL)
- {
- char pbuf[30];
- HP_TIMING_PRINT (buf, sizeof (buf), load_time);
- cp = _itoa ((1000ULL * load_time) / *rtld_total_timep,
- pbuf + sizeof (pbuf), 10, 0);
- wp = pbuf;
- switch (pbuf + sizeof (pbuf) - cp)
- {
- case 3:
- *wp++ = *cp++;
- case 2:
- *wp++ = *cp++;
- case 1:
- *wp++ = '.';
- *wp++ = *cp++;
- }
- *wp = '\0';
- _dl_debug_printf ("\
- time needed to load objects: %s (%s%%)\n",
- buf, pbuf);
- }
-#endif
-}
diff --git a/elf/setup-vdso.h b/elf/setup-vdso.h
deleted file mode 100644
index 2db597eba3..0000000000
--- a/elf/setup-vdso.h
+++ /dev/null
@@ -1,121 +0,0 @@
-/* Set up the data structures for the system-supplied DSO.
- Copyright (C) 2012-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-static inline void __attribute__ ((always_inline))
-setup_vdso (struct link_map *main_map __attribute__ ((unused)),
- struct link_map ***first_preload __attribute__ ((unused)))
-{
-#ifdef NEED_DL_SYSINFO_DSO
- if (GLRO(dl_sysinfo_dso) == NULL)
- return;
-
- /* Do an abridged version of the work _dl_map_object_from_fd would do
- to map in the object. It's already mapped and prelinked (and
- better be, since it's read-only and so we couldn't relocate it).
- We just want our data structures to describe it as if we had just
- mapped and relocated it normally. */
- struct link_map *l = _dl_new_object ((char *) "", "", lt_library, NULL,
- 0, LM_ID_BASE);
- if (__glibc_likely (l != NULL))
- {
- static ElfW(Dyn) dyn_temp[DL_RO_DYN_TEMP_CNT] attribute_relro;
-
- l->l_phdr = ((const void *) GLRO(dl_sysinfo_dso)
- + GLRO(dl_sysinfo_dso)->e_phoff);
- l->l_phnum = GLRO(dl_sysinfo_dso)->e_phnum;
- for (uint_fast16_t i = 0; i < l->l_phnum; ++i)
- {
- const ElfW(Phdr) *const ph = &l->l_phdr[i];
- if (ph->p_type == PT_DYNAMIC)
- {
- l->l_ld = (void *) ph->p_vaddr;
- l->l_ldnum = ph->p_memsz / sizeof (ElfW(Dyn));
- }
- else if (ph->p_type == PT_LOAD)
- {
- if (! l->l_addr)
- l->l_addr = ph->p_vaddr;
- if (ph->p_vaddr + ph->p_memsz >= l->l_map_end)
- l->l_map_end = ph->p_vaddr + ph->p_memsz;
- if ((ph->p_flags & PF_X)
- && ph->p_vaddr + ph->p_memsz >= l->l_text_end)
- l->l_text_end = ph->p_vaddr + ph->p_memsz;
- }
- else
- /* There must be no TLS segment. */
- assert (ph->p_type != PT_TLS);
- }
- l->l_map_start = (ElfW(Addr)) GLRO(dl_sysinfo_dso);
- l->l_addr = l->l_map_start - l->l_addr;
- l->l_map_end += l->l_addr;
- l->l_text_end += l->l_addr;
- l->l_ld = (void *) ((ElfW(Addr)) l->l_ld + l->l_addr);
- elf_get_dynamic_info (l, dyn_temp);
- _dl_setup_hash (l);
- l->l_relocated = 1;
-
- /* The vDSO is always used. */
- l->l_used = 1;
-
- /* Initialize l_local_scope to contain just this map. This allows
- the use of dl_lookup_symbol_x to resolve symbols within the vdso.
- So we create a single entry list pointing to l_real as its only
- element */
- l->l_local_scope[0]->r_nlist = 1;
- l->l_local_scope[0]->r_list = &l->l_real;
-
- /* Now that we have the info handy, use the DSO image's soname
- so this object can be looked up by name. Note that we do not
- set l_name here. That field gives the file name of the DSO,
- and this DSO is not associated with any file. */
- if (l->l_info[DT_SONAME] != NULL)
- {
- /* Work around a kernel problem. The kernel cannot handle
- addresses in the vsyscall DSO pages in writev() calls. */
- const char *dsoname = ((char *) D_PTR (l, l_info[DT_STRTAB])
- + l->l_info[DT_SONAME]->d_un.d_val);
- size_t len = strlen (dsoname) + 1;
- char *copy = malloc (len);
- if (copy == NULL)
- _dl_fatal_printf ("out of memory\n");
- l->l_libname->name = l->l_name = memcpy (copy, dsoname, len);
- }
-
- /* Add the vDSO to the object list. */
- _dl_add_to_namespace_list (l, LM_ID_BASE);
-
-# if IS_IN (rtld)
- /* Rearrange the list so this DSO appears after rtld_map. */
- assert (l->l_next == NULL);
- assert (l->l_prev == main_map);
- GL(dl_rtld_map).l_next = l;
- l->l_prev = &GL(dl_rtld_map);
- *first_preload = &l->l_next;
-# else
- GL(dl_nns) = 1;
-# endif
-
- /* We have a prelinked DSO preloaded by the system. */
- GLRO(dl_sysinfo_map) = l;
-# ifdef NEED_DL_SYSINFO
- if (GLRO(dl_sysinfo) == DL_SYSINFO_DEFAULT)
- GLRO(dl_sysinfo) = GLRO(dl_sysinfo_dso)->e_entry + l->l_addr;
-# endif
- }
-#endif
-}
diff --git a/elf/sln.c b/elf/sln.c
deleted file mode 100644
index af2d0de164..0000000000
--- a/elf/sln.c
+++ /dev/null
@@ -1,202 +0,0 @@
-/* `sln' program to create symbolic links between files.
- Copyright (C) 1998-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <error.h>
-#include <errno.h>
-#include <libintl.h>
-#include <locale.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <unistd.h>
-#include <errno.h>
-#include <ctype.h>
-#include <stdio.h>
-#include <string.h>
-#include <limits.h>
-
-#include "../version.h"
-
-#define PACKAGE _libc_intl_domainname
-
-static int makesymlink (const char *src, const char *dest);
-static int makesymlinks (const char *file);
-static void usage (void);
-
-int
-main (int argc, char **argv)
-{
- /* Set locale via LC_ALL. */
- setlocale (LC_ALL, "");
-
- /* Set the text message domain. */
- textdomain (PACKAGE);
-
- switch (argc)
- {
- case 2:
- if (strcmp (argv[1], "--version") == 0) {
- printf ("sln %s%s\n", PKGVERSION, VERSION);
- return 0;
- } else if (strcmp (argv[1], "--help") == 0) {
- usage ();
- return 0;
- }
- return makesymlinks (argv [1]);
- break;
-
- case 3:
- return makesymlink (argv [1], argv [2]);
- break;
-
- default:
- usage ();
- return 1;
- break;
- }
-}
-
-static void
-usage (void)
-{
- printf (_("Usage: sln src dest|file\n\n"));
- printf (_("For bug reporting instructions, please see:\n\
-%s.\n"), REPORT_BUGS_TO);
-}
-
-static int
-makesymlinks (const char *file)
-{
- char *buffer = NULL;
- size_t bufferlen = 0;
- int ret;
- int lineno;
- FILE *fp;
-
- if (strcmp (file, "-") == 0)
- fp = stdin;
- else
- {
- fp = fopen (file, "r");
- if (fp == NULL)
- {
- fprintf (stderr, _("%s: file open error: %m\n"), file);
- return 1;
- }
- }
-
- ret = 0;
- lineno = 0;
- while (!feof_unlocked (fp))
- {
- ssize_t n = getline (&buffer, &bufferlen, fp);
- char *src;
- char *dest;
- char *cp = buffer;
-
- if (n < 0)
- break;
- if (buffer[n - 1] == '\n')
- buffer[n - 1] = '\0';
-
- ++lineno;
- while (isspace (*cp))
- ++cp;
- if (*cp == '\0')
- /* Ignore empty lines. */
- continue;
- src = cp;
-
- do
- ++cp;
- while (*cp != '\0' && ! isspace (*cp));
- if (*cp != '\0')
- *cp++ = '\0';
-
- while (isspace (*cp))
- ++cp;
- if (*cp == '\0')
- {
- fprintf (stderr, _("No target in line %d\n"), lineno);
- ret = 1;
- continue;
- }
- dest = cp;
-
- do
- ++cp;
- while (*cp != '\0' && ! isspace (*cp));
- if (*cp != '\0')
- *cp++ = '\0';
-
- ret |= makesymlink (src, dest);
- }
- fclose (fp);
-
- return ret;
-}
-
-static int
-makesymlink (const char *src, const char *dest)
-{
- struct stat64 stats;
- const char *error;
-
- /* Destination must not be a directory. */
- if (lstat64 (dest, &stats) == 0)
- {
- if (S_ISDIR (stats.st_mode))
- {
- fprintf (stderr, _("%s: destination must not be a directory\n"),
- dest);
- return 1;
- }
- else if (unlink (dest) && errno != ENOENT)
- {
- fprintf (stderr, _("%s: failed to remove the old destination\n"),
- dest);
- return 1;
- }
- }
- else if (errno != ENOENT)
- {
- error = strerror (errno);
- fprintf (stderr, _("%s: invalid destination: %s\n"), dest, error);
- return -1;
- }
-
- if (symlink (src, dest) == 0)
- {
- /* Destination must exist by now. */
- if (access (dest, F_OK))
- {
- error = strerror (errno);
- unlink (dest);
- fprintf (stderr, _("Invalid link from \"%s\" to \"%s\": %s\n"),
- src, dest, error);
- return 1;
- }
- return 0;
- }
- else
- {
- error = strerror (errno);
- fprintf (stderr, _("Invalid link from \"%s\" to \"%s\": %s\n"),
- src, dest, error);
- return 1;
- }
-}
diff --git a/elf/sofini.c b/elf/sofini.c
deleted file mode 100644
index 13e74b7903..0000000000
--- a/elf/sofini.c
+++ /dev/null
@@ -1,19 +0,0 @@
-/* Finalizer module for ELF shared C library. This provides terminating
- null pointer words in the `.ctors' and `.dtors' sections. */
-
-#ifndef NO_CTORS_DTORS_SECTIONS
-static void (*const __CTOR_END__[1]) (void)
- __attribute__ ((used, section (".ctors")))
- = { 0 };
-static void (*const __DTOR_END__[1]) (void)
- __attribute__ ((used, section (".dtors")))
- = { 0 };
-#endif
-
-/* Terminate the frame unwind info section with a 4byte 0 as a sentinel;
- this would be the 'length' field in a real FDE. */
-
-typedef unsigned int ui32 __attribute__ ((mode (SI)));
-static const ui32 __FRAME_END__[1]
- __attribute__ ((used, section (".eh_frame")))
- = { 0 };
diff --git a/elf/soinit.c b/elf/soinit.c
deleted file mode 100644
index fe9935732b..0000000000
--- a/elf/soinit.c
+++ /dev/null
@@ -1,43 +0,0 @@
-/* Initializer module for building the ELF shared C library. This file and
- sofini.c do the work normally done by crtbeginS.o and crtendS.o, to wrap
- the `.ctors' and `.dtors' sections so the lists are terminated, and
- calling those lists of functions. */
-
-#ifndef NO_CTORS_DTORS_SECTIONS
-# include <stdlib.h>
-
-static void (*const __CTOR_LIST__[1]) (void)
- __attribute__ ((used, section (".ctors")))
- = { (void (*) (void)) -1 };
-static void (*const __DTOR_LIST__[1]) (void)
- __attribute__ ((used, section (".dtors")))
- = { (void (*) (void)) -1 };
-
-static inline void
-run_hooks (void (*const list[]) (void))
-{
- while (*++list)
- (**list) ();
-}
-
-/* This function will be called from _init in init-first.c. */
-void
-__libc_global_ctors (void)
-{
- /* Call constructor functions. */
- run_hooks (__CTOR_LIST__);
-}
-
-
-/* This function becomes the DT_FINI termination function
- for the C library. */
-void
-__libc_fini (void)
-{
- /* Call destructor functions. */
- run_hooks (__DTOR_LIST__);
-}
-
-void (*_fini_ptr) (void) __attribute__ ((section (".fini_array")))
- = &__libc_fini;
-#endif
diff --git a/elf/sotruss-lib.c b/elf/sotruss-lib.c
deleted file mode 100644
index da2fedd52a..0000000000
--- a/elf/sotruss-lib.c
+++ /dev/null
@@ -1,386 +0,0 @@
-/* Trace calls through PLTs and show caller, callee, and parameters.
- Copyright (C) 2011-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@gmail.com>, 2011.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <error.h>
-#include <fcntl.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/param.h>
-#include <sys/uio.h>
-
-#include <ldsodefs.h>
-
-
-extern const char *__progname;
-extern const char *__progname_full;
-
-
-/* List of objects to trace calls from. */
-static const char *fromlist;
-/* List of objects to trace calls to. */
-static const char *tolist;
-
-/* If non-zero, also trace returns of the calls. */
-static int do_exit;
-/* If non-zero print PID for each line. */
-static int print_pid;
-
-/* The output stream to use. */
-static FILE *out_file;
-
-
-static int
-match_pid (pid_t pid, const char *which)
-{
- if (which == NULL || which[0] == '\0')
- {
- print_pid = 1;
- return 1;
- }
-
- char *endp;
- unsigned long n = strtoul (which, &endp, 0);
- return *endp == '\0' && n == pid;
-}
-
-
-static void
-init (void)
-{
- fromlist = getenv ("SOTRUSS_FROMLIST");
- if (fromlist != NULL && fromlist[0] == '\0')
- fromlist = NULL;
- tolist = getenv ("SOTRUSS_TOLIST");
- if (tolist != NULL && tolist[0] == '\0')
- tolist = NULL;
- do_exit = (getenv ("SOTRUSS_EXIT") ?: "")[0] != '\0';
-
- /* Determine whether this process is supposed to be traced and if
- yes, whether we should print into a file. */
- const char *which_process = getenv ("SOTRUSS_WHICH");
- pid_t pid = getpid ();
- int out_fd = -1;
- if (match_pid (pid, which_process))
- {
- const char *out_filename = getenv ("SOTRUSS_OUTNAME");
-
- if (out_filename != NULL && out_filename[0] != 0)
- {
- size_t out_filename_len = strlen (out_filename) + 13;
- char fullname[out_filename_len];
- char *endp = stpcpy (fullname, out_filename);
- if (which_process == NULL || which_process[0] == '\0')
- snprintf (endp, 13, ".%ld", (long int) pid);
-
- out_fd = open (fullname, O_RDWR | O_CREAT | O_TRUNC, 0666);
- if (out_fd != -1)
- print_pid = 0;
- }
- }
-
- /* If we do not write into a file write to stderr. Duplicate the
- descriptor so that we can keep printing in case the program
- closes stderr. Try first to allocate a descriptor with a value
- usually not used as to minimize interference with the
- program. */
- if (out_fd == -1)
- {
- out_fd = fcntl (STDERR_FILENO, F_DUPFD, 1000);
- if (out_fd == -1)
- out_fd = dup (STDERR_FILENO);
- }
-
- if (out_fd != -1)
- {
- /* Convert file descriptor into a stream. */
- out_file = fdopen (out_fd, "w");
- if (out_file != NULL)
- setlinebuf (out_file);
- }
-}
-
-
-/* Audit interface verification. We also initialize everything if
- everything checks out OK. */
-unsigned int
-la_version (unsigned int v)
-{
- if (v != LAV_CURRENT)
- error (1, 0, "cannot handle interface version %u", v);
-
- init ();
-
- return v;
-}
-
-
-/* Check whether a file name is on the colon-separated list of file
- names. */
-static unsigned int
-match_file (const char *list, const char *name, size_t name_len,
- unsigned int mask)
-{
- if (list[0] == '\0')
- return 0;
-
- const char *cp = list;
- while (1)
- {
- if (strncmp (cp, name, name_len) == 0
- && (cp[name_len] == ':' || cp[name_len] == '\0'))
- return mask;
-
- cp = strchr (cp, ':');
- if (cp == NULL)
- return 0;
- ++cp;
- }
-}
-
-
-unsigned int
-la_objopen (struct link_map *map, Lmid_t lmid, uintptr_t *cookie)
-{
- if (out_file == NULL)
- return 0;
-
- const char *full_name = map->l_name ?: "";
- if (full_name[0] == '\0')
- full_name = __progname_full;
- size_t full_name_len = strlen (full_name);
- const char *base_name = basename (full_name);
- if (base_name[0] == '\0')
- base_name = __progname;
- size_t base_name_len = strlen (base_name);
-
- int result = 0;
- const char *print_name = NULL;
- for (struct libname_list *l = map->l_libname; l != NULL; l = l->next)
- {
- if (print_name == NULL || (print_name[0] == '/' && l->name[0] != '/'))
- print_name = l->name;
-
- if (fromlist != NULL)
- result |= match_file (fromlist, l->name, strlen (l->name),
- LA_FLG_BINDFROM);
-
- if (tolist != NULL)
- result |= match_file (tolist, l->name, strlen (l->name),LA_FLG_BINDTO);
- }
-
- if (print_name == NULL)
- print_name = base_name;
- if (print_name[0] == '\0')
- print_name = __progname;
-
- /* We cannot easily get to the object name in the PLT handling
- functions. Use the cookie to get the string pointer passed back
- to us. */
- *cookie = (uintptr_t) print_name;
-
- /* The object name has to be on the list of objects to trace calls
- from or that list must be empty. In the latter case we trace
- only calls from the main binary. */
- if (fromlist == NULL)
- result |= map->l_name[0] == '\0' ? LA_FLG_BINDFROM : 0;
- else
- result |= (match_file (fromlist, full_name, full_name_len,
- LA_FLG_BINDFROM)
- | match_file (fromlist, base_name, base_name_len,
- LA_FLG_BINDFROM));
-
- /* The object name has to be on the list of objects to trace calls
- to or that list must be empty. In the latter case we trace
- calls toall objects. */
- if (tolist == NULL)
- result |= LA_FLG_BINDTO;
- else
- result |= (match_file (tolist, full_name, full_name_len, LA_FLG_BINDTO)
- | match_file (tolist, base_name, base_name_len, LA_FLG_BINDTO));
-
- return result;
-}
-
-
-#if __ELF_NATIVE_CLASS == 32
-# define la_symbind la_symbind32
-typedef Elf32_Sym Elf_Sym;
-#else
-# define la_symbind la_symbind64
-typedef Elf64_Sym Elf_Sym;
-#endif
-
-uintptr_t
-la_symbind (Elf_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, unsigned int *flags, const char *symname)
-{
- if (!do_exit)
- *flags = LA_SYMB_NOPLTEXIT;
-
- return sym->st_value;
-}
-
-
-static void
-print_enter (uintptr_t *refcook, uintptr_t *defcook, const char *symname,
- unsigned long int reg1, unsigned long int reg2,
- unsigned long int reg3, unsigned int flags)
-{
- char buf[3 * sizeof (pid_t) + 3];
- buf[0] = '\0';
- if (print_pid)
- snprintf (buf, sizeof (buf), "%5ld: ", (long int) getpid ());
-
- fprintf (out_file, "%s%15s -> %-15s:%s%s(0x%lx, 0x%lx, 0x%lx)\n",
- buf, (char *) *refcook, (char *) *defcook,
- (flags & LA_SYMB_NOPLTEXIT) ? "*" : " ", symname, reg1, reg2, reg3);
-}
-
-
-#ifdef __i386__
-Elf32_Addr
-la_i86_gnu_pltenter (Elf32_Sym *sym __attribute__ ((unused)),
- unsigned int ndx __attribute__ ((unused)),
- uintptr_t *refcook, uintptr_t *defcook,
- La_i86_regs *regs, unsigned int *flags,
- const char *symname, long int *framesizep)
-{
- unsigned long int *sp = (unsigned long int *) regs->lr_esp;
-
- print_enter (refcook, defcook, symname, sp[1], sp[2], sp[3], *flags);
-
- /* No need to copy anything, we will not need the parameters in any case. */
- *framesizep = 0;
-
- return sym->st_value;
-}
-#elif defined __x86_64__
-Elf64_Addr
-la_x86_64_gnu_pltenter (Elf64_Sym *sym __attribute__ ((unused)),
- unsigned int ndx __attribute__ ((unused)),
- uintptr_t *refcook, uintptr_t *defcook,
- La_x86_64_regs *regs, unsigned int *flags,
- const char *symname, long int *framesizep)
-{
- print_enter (refcook, defcook, symname,
- regs->lr_rdi, regs->lr_rsi, regs->lr_rdx, *flags);
-
- /* No need to copy anything, we will not need the parameters in any case. */
- *framesizep = 0;
-
- return sym->st_value;
-}
-#elif defined __sparc__ && !defined __arch64__
-Elf32_Addr
-la_sparc32_gnu_pltenter (Elf32_Sym *sym __attribute__ ((unused)),
- unsigned int ndx __attribute__ ((unused)),
- uintptr_t *refcook, uintptr_t *defcook,
- La_sparc32_regs *regs, unsigned int *flags,
- const char *symname, long int *framesizep)
-{
- print_enter (refcook, defcook, symname,
- regs->lr_reg[0], regs->lr_reg[1], regs->lr_reg[2],
- *flags);
-
- /* No need to copy anything, we will not need the parameters in any case. */
- *framesizep = 0;
-
- return sym->st_value;
-}
-#elif defined __sparc__ && defined __arch64__
-Elf64_Addr
-la_sparc64_gnu_pltenter (Elf64_Sym *sym __attribute__ ((unused)),
- unsigned int ndx __attribute__ ((unused)),
- uintptr_t *refcook, uintptr_t *defcook,
- La_sparc64_regs *regs, unsigned int *flags,
- const char *symname, long int *framesizep)
-{
- print_enter (refcook, defcook, symname,
- regs->lr_reg[0], regs->lr_reg[1], regs->lr_reg[2],
- *flags);
-
- /* No need to copy anything, we will not need the parameters in any case. */
- *framesizep = 0;
-
- return sym->st_value;
-}
-#elif !defined HAVE_ARCH_PLTENTER
-# warning "pltenter for architecture not supported"
-#endif
-
-
-static void
-print_exit (uintptr_t *refcook, uintptr_t *defcook, const char *symname,
- unsigned long int reg)
-{
- char buf[3 * sizeof (pid_t) + 3];
- buf[0] = '\0';
- if (print_pid)
- snprintf (buf, sizeof (buf), "%5ld: ", (long int) getpid ());
-
- fprintf (out_file, "%s%15s -> %-15s:%s%s - 0x%lx\n",
- buf, (char *) *refcook, (char *) *defcook, " ", symname, reg);
-}
-
-
-#ifdef __i386__
-unsigned int
-la_i86_gnu_pltexit (Elf32_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, const struct La_i86_regs *inregs,
- struct La_i86_retval *outregs, const char *symname)
-{
- print_exit (refcook, defcook, symname, outregs->lrv_eax);
-
- return 0;
-}
-#elif defined __x86_64__
-unsigned int
-la_x86_64_gnu_pltexit (Elf64_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, const struct La_x86_64_regs *inregs,
- struct La_x86_64_retval *outregs, const char *symname)
-{
- print_exit (refcook, defcook, symname, outregs->lrv_rax);
-
- return 0;
-}
-#elif defined __sparc__ && !defined __arch64__
-unsigned int
-la_sparc32_gnu_pltexit (Elf32_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, const struct La_sparc32_regs *inregs,
- struct La_sparc32_retval *outregs, const char *symname)
-{
- print_exit (refcook, defcook, symname, outregs->lrv_reg[0]);
-
- return 0;
-}
-#elif defined __sparc__ && defined __arch64__
-unsigned int
-la_sparc64_gnu_pltexit (Elf64_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, const struct La_sparc64_regs *inregs,
- struct La_sparc64_retval *outregs, const char *symname)
-{
- print_exit (refcook, defcook, symname, outregs->lrv_reg[0]);
-
- return 0;
-}
-#elif !defined HAVE_ARCH_PLTEXIT
-# warning "pltexit for architecture not supported"
-#endif
diff --git a/elf/sotruss.sh b/elf/sotruss.sh
deleted file mode 100755
index c83e837e0e..0000000000
--- a/elf/sotruss.sh
+++ /dev/null
@@ -1,152 +0,0 @@
-#! @BASH@
-# Copyright (C) 2011-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-# We should be able to find the translation right at the beginning.
-TEXTDOMAIN=libc
-TEXTDOMAINDIR=@TEXTDOMAINDIR@
-
-unset SOTRUSS_FROMLIST
-unset SOTRUSS_TOLIST
-unset SOTRUSS_OUTNAME
-unset SOTRUSS_EXIT
-unset SOTRUSS_NOINDENT
-SOTRUSS_WHICH=$$
-lib='@PREFIX@/$LIB/audit/sotruss-lib.so'
-
-do_help() {
- echo $"Usage: sotruss [OPTION...] [--] EXECUTABLE [EXECUTABLE-OPTION...]
- -F, --from FROMLIST Trace calls from objects on FROMLIST
- -T, --to TOLIST Trace calls to objects on TOLIST
-
- -e, --exit Also show exits from the function calls
- -f, --follow Trace child processes
- -o, --output FILENAME Write output to FILENAME (or FILENAME.$PID in case
- -f is also used) instead of standard error
-
- -?, --help Give this help list
- --usage Give a short usage message
- --version Print program version"
-
- echo
- printf $"Mandatory arguments to long options are also mandatory for any corresponding\nshort options.\n"
- echo
-
- printf $"For bug reporting instructions, please see:\\n%s.\\n" \
- "@REPORT_BUGS_TO@"
- exit 0
-}
-
-do_missing_arg() {
- printf >&2 $"%s: option requires an argument -- '%s'\n" sotruss "$1"
- printf >&2 $"Try \`%s --help' or \`%s --usage' for more information.\n" sotruss sotruss
- exit 1
-}
-
-do_ambiguous() {
- printf >&2 $"%s: option is ambiguous; possibilities:"
- while test $# -gt 0; do
- printf >&2 " '%s'" $1
- shift
- done
- printf >&2 "\n"
- printf >&2 $"Try \`%s --help' or \`%s --usage' for more information.\n" sotruss sotruss
- exit 1
-}
-
-while test $# -gt 0; do
- case "$1" in
- --v | --ve | --ver | --vers | --versi | --versio | --version)
- echo "sotruss @PKGVERSION@@VERSION@"
- printf $"Copyright (C) %s Free Software Foundation, Inc.
-This is free software; see the source for copying conditions. There is NO
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
-" "2017"
- printf $"Written by %s.\n" "Ulrich Drepper"
- exit 0
- ;;
- -\? | --h | --he | --hel | --help)
- do_help
- ;;
- --u | --us | --usa | --usag | --usage)
- printf $"Usage: %s [-ef] [-F FROMLIST] [-o FILENAME] [-T TOLIST] [--exit]
- [--follow] [--from FROMLIST] [--output FILENAME] [--to TOLIST]
- [--help] [--usage] [--version] [--]
- EXECUTABLE [EXECUTABLE-OPTION...]\n" sotruss
- exit 0
- ;;
- -F | --fr | --fro | --from)
- if test $# -eq 1; then
- do_missing_arg "$1"
- fi
- shift
- SOTRUSS_FROMLIST="$1"
- ;;
- -T | --t | --to)
- if test $# -eq 1; then
- do_missing_arg "$1"
- fi
- shift
- SOTRUSS_TOLIST="$1"
- ;;
- -o | --o | --ou | --out | --outp | --outpu | --output)
- if test $# -eq 1; then
- do_missing_arg "$1"
- fi
- shift
- SOTRUSS_OUTNAME="$1"
- ;;
- -f | --fo | --fol | --foll | --follo | --follow)
- unset SOTRUSS_WHICH
- ;;
- -l | --l | --li | --lib)
- if test $# -eq 1; then
- do_missing_arg "$1"
- fi
- shift
- lib="$1"
- ;;
- -e | --e | --ex | --exi | --exit)
- SOTRUSS_EXIT=1
- ;;
- --f)
- do_ambiguous '--from' '--follow'
- ;;
- --)
- shift
- break
- ;;
- -*)
- printf >&2 $"%s: unrecognized option '%c%s'\n" sotruss '-' ${1#-}
- printf >&2 $"Try \`%s --help' or \`%s --usage' for more information.\n" sotruss sotruss
- exit 1
- ;;
- *)
- break
- ;;
- esac
- shift
-done
-
-export SOTRUSS_FROMLIST
-export SOTRUSS_TOLIST
-export SOTRUSS_OUTNAME
-export SOTRUSS_WHICH
-export SOTRUSS_EXIT
-export LD_AUDIT="$lib"
-
-exec "$@"
diff --git a/elf/sprof.c b/elf/sprof.c
deleted file mode 100644
index 85c4975360..0000000000
--- a/elf/sprof.c
+++ /dev/null
@@ -1,1436 +0,0 @@
-/* Read and display shared object profiling data.
- Copyright (C) 1997-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <argp.h>
-#include <dlfcn.h>
-#include <elf.h>
-#include <error.h>
-#include <fcntl.h>
-#include <inttypes.h>
-#include <libintl.h>
-#include <locale.h>
-#include <obstack.h>
-#include <search.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdint.h>
-#include <ldsodefs.h>
-#include <sys/gmon.h>
-#include <sys/gmon_out.h>
-#include <sys/mman.h>
-#include <sys/param.h>
-#include <sys/stat.h>
-
-/* Get libc version number. */
-#include "../version.h"
-
-#define PACKAGE _libc_intl_domainname
-
-
-#include <endian.h>
-#if BYTE_ORDER == BIG_ENDIAN
-# define byteorder ELFDATA2MSB
-# define byteorder_name "big-endian"
-#elif BYTE_ORDER == LITTLE_ENDIAN
-# define byteorder ELFDATA2LSB
-# define byteorder_name "little-endian"
-#else
-# error "Unknown BYTE_ORDER " BYTE_ORDER
-# define byteorder ELFDATANONE
-#endif
-
-#ifndef PATH_MAX
-# define PATH_MAX 1024
-#endif
-
-
-extern int __profile_frequency (void);
-
-/* Name and version of program. */
-static void print_version (FILE *stream, struct argp_state *state);
-void (*argp_program_version_hook) (FILE *, struct argp_state *) = print_version;
-
-#define OPT_TEST 1
-
-/* Definitions of arguments for argp functions. */
-static const struct argp_option options[] =
-{
- { NULL, 0, NULL, 0, N_("Output selection:") },
- { "call-pairs", 'c', NULL, 0,
- N_("print list of count paths and their number of use") },
- { "flat-profile", 'p', NULL, 0,
- N_("generate flat profile with counts and ticks") },
- { "graph", 'q', NULL, 0, N_("generate call graph") },
-
- { "test", OPT_TEST, NULL, OPTION_HIDDEN, NULL },
- { NULL, 0, NULL, 0, NULL }
-};
-
-/* Short description of program. */
-static const char doc[] = N_("Read and display shared object profiling data.");
-//For bug reporting instructions, please see:\n
-//<http://www.gnu.org/software/libc/bugs.html>.\n");
-
-/* Strings for arguments in help texts. */
-static const char args_doc[] = N_("SHOBJ [PROFDATA]");
-
-/* Prototype for option handler. */
-static error_t parse_opt (int key, char *arg, struct argp_state *state);
-
-/* Function to print some extra text in the help message. */
-static char *more_help (int key, const char *text, void *input);
-
-/* Data structure to communicate with argp functions. */
-static struct argp argp =
-{
- options, parse_opt, args_doc, doc, NULL, more_help
-};
-
-
-/* Operation modes. */
-static enum
-{
- NONE = 0,
- FLAT_MODE = 1 << 0,
- CALL_GRAPH_MODE = 1 << 1,
- CALL_PAIRS = 1 << 2,
-
- DEFAULT_MODE = FLAT_MODE | CALL_GRAPH_MODE
-} mode;
-
-/* Nozero for testing. */
-static int do_test;
-
-/* Strcuture describing calls. */
-struct here_fromstruct
-{
- struct here_cg_arc_record volatile *here;
- uint16_t link;
-};
-
-/* We define a special type to address the elements of the arc table.
- This is basically the `gmon_cg_arc_record' format but it includes
- the room for the tag and it uses real types. */
-struct here_cg_arc_record
-{
- uintptr_t from_pc;
- uintptr_t self_pc;
- uint32_t count;
-} __attribute__ ((packed));
-
-
-struct known_symbol;
-struct arc_list
-{
- size_t idx;
- uintmax_t count;
-
- struct arc_list *next;
-};
-
-static struct obstack ob_list;
-
-
-struct known_symbol
-{
- const char *name;
- uintptr_t addr;
- size_t size;
- bool weak;
- bool hidden;
-
- uintmax_t ticks;
- uintmax_t calls;
-
- struct arc_list *froms;
- struct arc_list *tos;
-};
-
-
-struct shobj
-{
- const char *name; /* User-provided name. */
-
- struct link_map *map;
- const char *dynstrtab; /* Dynamic string table of shared object. */
- const char *soname; /* Soname of shared object. */
-
- uintptr_t lowpc;
- uintptr_t highpc;
- unsigned long int kcountsize;
- size_t expected_size; /* Expected size of profiling file. */
- size_t tossize;
- size_t fromssize;
- size_t fromlimit;
- unsigned int hashfraction;
- int s_scale;
-
- void *symbol_map;
- size_t symbol_mapsize;
- const ElfW(Sym) *symtab;
- size_t symtab_size;
- const char *strtab;
-
- struct obstack ob_str;
- struct obstack ob_sym;
-};
-
-
-struct real_gmon_hist_hdr
-{
- char *low_pc;
- char *high_pc;
- int32_t hist_size;
- int32_t prof_rate;
- char dimen[15];
- char dimen_abbrev;
-};
-
-
-struct profdata
-{
- void *addr;
- off_t size;
-
- char *hist;
- struct real_gmon_hist_hdr *hist_hdr;
- uint16_t *kcount;
- uint32_t narcs; /* Number of arcs in toset. */
- struct here_cg_arc_record *data;
- uint16_t *tos;
- struct here_fromstruct *froms;
-};
-
-/* Search tree for symbols. */
-static void *symroot;
-static struct known_symbol **sortsym;
-static size_t symidx;
-static uintmax_t total_ticks;
-
-/* Prototypes for local functions. */
-static struct shobj *load_shobj (const char *name);
-static void unload_shobj (struct shobj *shobj);
-static struct profdata *load_profdata (const char *name, struct shobj *shobj);
-static void unload_profdata (struct profdata *profdata);
-static void count_total_ticks (struct shobj *shobj, struct profdata *profdata);
-static void count_calls (struct shobj *shobj, struct profdata *profdata);
-static void read_symbols (struct shobj *shobj);
-static void add_arcs (struct profdata *profdata);
-static void generate_flat_profile (struct profdata *profdata);
-static void generate_call_graph (struct profdata *profdata);
-static void generate_call_pair_list (struct profdata *profdata);
-
-
-int
-main (int argc, char *argv[])
-{
- const char *shobj;
- const char *profdata;
- struct shobj *shobj_handle;
- struct profdata *profdata_handle;
- int remaining;
-
- setlocale (LC_ALL, "");
-
- /* Initialize the message catalog. */
- textdomain (_libc_intl_domainname);
-
- /* Parse and process arguments. */
- argp_parse (&argp, argc, argv, 0, &remaining, NULL);
-
- if (argc - remaining == 0 || argc - remaining > 2)
- {
- /* We need exactly two non-option parameter. */
- argp_help (&argp, stdout, ARGP_HELP_SEE | ARGP_HELP_EXIT_ERR,
- program_invocation_short_name);
- exit (1);
- }
-
- /* Get parameters. */
- shobj = argv[remaining];
- if (argc - remaining == 2)
- profdata = argv[remaining + 1];
- else
- /* No filename for the profiling data given. We will determine it
- from the soname of the shobj, later. */
- profdata = NULL;
-
- /* First see whether we can load the shared object. */
- shobj_handle = load_shobj (shobj);
- if (shobj_handle == NULL)
- exit (1);
-
- /* We can now determine the filename for the profiling data, if
- nececessary. */
- if (profdata == NULL)
- {
- char *newp;
- const char *soname;
- size_t soname_len;
-
- soname = shobj_handle->soname ?: basename (shobj);
- soname_len = strlen (soname);
- newp = (char *) alloca (soname_len + sizeof ".profile");
- stpcpy (mempcpy (newp, soname, soname_len), ".profile");
- profdata = newp;
- }
-
- /* Now see whether the profiling data file matches the given object. */
- profdata_handle = load_profdata (profdata, shobj_handle);
- if (profdata_handle == NULL)
- {
- unload_shobj (shobj_handle);
-
- exit (1);
- }
-
- read_symbols (shobj_handle);
-
- /* Count the ticks. */
- count_total_ticks (shobj_handle, profdata_handle);
-
- /* Count the calls. */
- count_calls (shobj_handle, profdata_handle);
-
- /* Add the arc information. */
- add_arcs (profdata_handle);
-
- /* If no mode is specified fall back to the default mode. */
- if (mode == NONE)
- mode = DEFAULT_MODE;
-
- /* Do some work. */
- if (mode & FLAT_MODE)
- generate_flat_profile (profdata_handle);
-
- if (mode & CALL_GRAPH_MODE)
- generate_call_graph (profdata_handle);
-
- if (mode & CALL_PAIRS)
- generate_call_pair_list (profdata_handle);
-
- /* Free the resources. */
- unload_shobj (shobj_handle);
- unload_profdata (profdata_handle);
-
- return 0;
-}
-
-
-/* Handle program arguments. */
-static error_t
-parse_opt (int key, char *arg, struct argp_state *state)
-{
- switch (key)
- {
- case 'c':
- mode |= CALL_PAIRS;
- break;
- case 'p':
- mode |= FLAT_MODE;
- break;
- case 'q':
- mode |= CALL_GRAPH_MODE;
- break;
- case OPT_TEST:
- do_test = 1;
- break;
- default:
- return ARGP_ERR_UNKNOWN;
- }
- return 0;
-}
-
-
-static char *
-more_help (int key, const char *text, void *input)
-{
- char *tp = NULL;
- switch (key)
- {
- case ARGP_KEY_HELP_EXTRA:
- /* We print some extra information. */
- if (asprintf (&tp, gettext ("\
-For bug reporting instructions, please see:\n\
-%s.\n"), REPORT_BUGS_TO) < 0)
- return NULL;
- return tp;
- default:
- break;
- }
- return (char *) text;
-}
-
-
-/* Print the version information. */
-static void
-print_version (FILE *stream, struct argp_state *state)
-{
- fprintf (stream, "sprof %s%s\n", PKGVERSION, VERSION);
- fprintf (stream, gettext ("\
-Copyright (C) %s Free Software Foundation, Inc.\n\
-This is free software; see the source for copying conditions. There is NO\n\
-warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\
-"),
- "2017");
- fprintf (stream, gettext ("Written by %s.\n"), "Ulrich Drepper");
-}
-
-
-/* Note that we must not use `dlopen' etc. The shobj object must not
- be loaded for use. */
-static struct shobj *
-load_shobj (const char *name)
-{
- struct link_map *map = NULL;
- struct shobj *result;
- ElfW(Addr) mapstart = ~((ElfW(Addr)) 0);
- ElfW(Addr) mapend = 0;
- const ElfW(Phdr) *ph;
- size_t textsize;
- ElfW(Ehdr) *ehdr;
- int fd;
- ElfW(Shdr) *shdr;
- size_t pagesize = getpagesize ();
-
- /* Since we use dlopen() we must be prepared to work around the sometimes
- strange lookup rules for the shared objects. If we have a file foo.so
- in the current directory and the user specfies foo.so on the command
- line (without specifying a directory) we should load the file in the
- current directory even if a normal dlopen() call would read the other
- file. We do this by adding a directory portion to the name. */
- if (strchr (name, '/') == NULL)
- {
- char *load_name = (char *) alloca (strlen (name) + 3);
- stpcpy (stpcpy (load_name, "./"), name);
-
- map = (struct link_map *) dlopen (load_name, RTLD_LAZY | __RTLD_SPROF);
- }
- if (map == NULL)
- {
- map = (struct link_map *) dlopen (name, RTLD_LAZY | __RTLD_SPROF);
- if (map == NULL)
- {
- error (0, errno, _("failed to load shared object `%s'"), name);
- return NULL;
- }
- }
-
- /* Prepare the result. */
- result = (struct shobj *) calloc (1, sizeof (struct shobj));
- if (result == NULL)
- {
- error (0, errno, _("cannot create internal descriptor"));
- dlclose (map);
- return NULL;
- }
- result->name = name;
- result->map = map;
-
- /* Compute the size of the sections which contain program code.
- This must match the code in dl-profile.c (_dl_start_profile). */
- for (ph = map->l_phdr; ph < &map->l_phdr[map->l_phnum]; ++ph)
- if (ph->p_type == PT_LOAD && (ph->p_flags & PF_X))
- {
- ElfW(Addr) start = (ph->p_vaddr & ~(pagesize - 1));
- ElfW(Addr) end = ((ph->p_vaddr + ph->p_memsz + pagesize - 1)
- & ~(pagesize - 1));
-
- if (start < mapstart)
- mapstart = start;
- if (end > mapend)
- mapend = end;
- }
-
- result->lowpc = ROUNDDOWN ((uintptr_t) (mapstart + map->l_addr),
- HISTFRACTION * sizeof (HISTCOUNTER));
- result->highpc = ROUNDUP ((uintptr_t) (mapend + map->l_addr),
- HISTFRACTION * sizeof (HISTCOUNTER));
- if (do_test)
- printf ("load addr: %0#*" PRIxPTR "\n"
- "lower bound PC: %0#*" PRIxPTR "\n"
- "upper bound PC: %0#*" PRIxPTR "\n",
- __ELF_NATIVE_CLASS == 32 ? 10 : 18, map->l_addr,
- __ELF_NATIVE_CLASS == 32 ? 10 : 18, result->lowpc,
- __ELF_NATIVE_CLASS == 32 ? 10 : 18, result->highpc);
-
- textsize = result->highpc - result->lowpc;
- result->kcountsize = textsize / HISTFRACTION;
- result->hashfraction = HASHFRACTION;
- if (do_test)
- printf ("hashfraction = %d\ndivider = %Zu\n",
- result->hashfraction,
- result->hashfraction * sizeof (struct here_fromstruct));
- result->tossize = textsize / HASHFRACTION;
- result->fromlimit = textsize * ARCDENSITY / 100;
- if (result->fromlimit < MINARCS)
- result->fromlimit = MINARCS;
- if (result->fromlimit > MAXARCS)
- result->fromlimit = MAXARCS;
- result->fromssize = result->fromlimit * sizeof (struct here_fromstruct);
-
- result->expected_size = (sizeof (struct gmon_hdr)
- + 4 + sizeof (struct gmon_hist_hdr)
- + result->kcountsize
- + 4 + 4
- + (result->fromssize
- * sizeof (struct here_cg_arc_record)));
-
- if (do_test)
- printf ("expected size: %Zd\n", result->expected_size);
-
-#define SCALE_1_TO_1 0x10000L
-
- if (result->kcountsize < result->highpc - result->lowpc)
- {
- size_t range = result->highpc - result->lowpc;
- size_t quot = range / result->kcountsize;
-
- if (quot >= SCALE_1_TO_1)
- result->s_scale = 1;
- else if (quot >= SCALE_1_TO_1 / 256)
- result->s_scale = SCALE_1_TO_1 / quot;
- else if (range > ULONG_MAX / 256)
- result->s_scale = ((SCALE_1_TO_1 * 256)
- / (range / (result->kcountsize / 256)));
- else
- result->s_scale = ((SCALE_1_TO_1 * 256)
- / ((range * 256) / result->kcountsize));
- }
- else
- result->s_scale = SCALE_1_TO_1;
-
- if (do_test)
- printf ("s_scale: %d\n", result->s_scale);
-
- /* Determine the dynamic string table. */
- if (map->l_info[DT_STRTAB] == NULL)
- result->dynstrtab = NULL;
- else
- result->dynstrtab = (const char *) D_PTR (map, l_info[DT_STRTAB]);
- if (do_test)
- printf ("string table: %p\n", result->dynstrtab);
-
- /* Determine the soname. */
- if (map->l_info[DT_SONAME] == NULL)
- result->soname = NULL;
- else
- result->soname = result->dynstrtab + map->l_info[DT_SONAME]->d_un.d_val;
- if (do_test && result->soname != NULL)
- printf ("soname: %s\n", result->soname);
-
- /* Now we have to load the symbol table.
-
- First load the section header table. */
- ehdr = (ElfW(Ehdr) *) map->l_map_start;
-
- /* Make sure we are on the right party. */
- if (ehdr->e_shentsize != sizeof (ElfW(Shdr)))
- abort ();
-
- /* And we need the shared object file descriptor again. */
- fd = open (map->l_name, O_RDONLY);
- if (fd == -1)
- /* Dooh, this really shouldn't happen. We know the file is available. */
- error (EXIT_FAILURE, errno, _("Reopening shared object `%s' failed"),
- map->l_name);
-
- /* Map the section header. */
- size_t size = ehdr->e_shnum * sizeof (ElfW(Shdr));
- shdr = (ElfW(Shdr) *) alloca (size);
- if (pread (fd, shdr, size, ehdr->e_shoff) != size)
- error (EXIT_FAILURE, errno, _("reading of section headers failed"));
-
- /* Get the section header string table. */
- char *shstrtab = (char *) alloca (shdr[ehdr->e_shstrndx].sh_size);
- if (pread (fd, shstrtab, shdr[ehdr->e_shstrndx].sh_size,
- shdr[ehdr->e_shstrndx].sh_offset)
- != shdr[ehdr->e_shstrndx].sh_size)
- error (EXIT_FAILURE, errno,
- _("reading of section header string table failed"));
-
- /* Search for the ".symtab" section. */
- ElfW(Shdr) *symtab_entry = NULL;
- ElfW(Shdr) *debuglink_entry = NULL;
- for (int idx = 0; idx < ehdr->e_shnum; ++idx)
- if (shdr[idx].sh_type == SHT_SYMTAB
- && strcmp (shstrtab + shdr[idx].sh_name, ".symtab") == 0)
- {
- symtab_entry = &shdr[idx];
- break;
- }
- else if (shdr[idx].sh_type == SHT_PROGBITS
- && strcmp (shstrtab + shdr[idx].sh_name, ".gnu_debuglink") == 0)
- debuglink_entry = &shdr[idx];
-
- /* Get the file name of the debuginfo file if necessary. */
- int symfd = fd;
- if (symtab_entry == NULL && debuglink_entry != NULL)
- {
- size_t size = debuglink_entry->sh_size;
- char *debuginfo_fname = (char *) alloca (size + 1);
- debuginfo_fname[size] = '\0';
- if (pread (fd, debuginfo_fname, size, debuglink_entry->sh_offset)
- != size)
- {
- fprintf (stderr, _("*** Cannot read debuginfo file name: %m\n"));
- goto no_debuginfo;
- }
-
- static const char procpath[] = "/proc/self/fd/%d";
- char origprocname[sizeof (procpath) + sizeof (int) * 3];
- snprintf (origprocname, sizeof (origprocname), procpath, fd);
- char *origlink = (char *) alloca (PATH_MAX);
- ssize_t n = readlink (origprocname, origlink, PATH_MAX - 1);
- if (n == -1)
- goto no_debuginfo;
- origlink[n] = '\0';
-
- /* Try to find the actual file. There are three places:
- 1. the same directory the DSO is in
- 2. in a subdir named .debug of the directory the DSO is in
- 3. in /usr/lib/debug/PATH-OF-DSO
- */
- char *realname = canonicalize_file_name (origlink);
- char *cp = NULL;
- if (realname == NULL || (cp = strrchr (realname, '/')) == NULL)
- error (EXIT_FAILURE, errno, _("cannot determine file name"));
-
- /* Leave the last slash in place. */
- *++cp = '\0';
-
- /* First add the debuginfo file name only. */
- static const char usrlibdebug[]= "/usr/lib/debug/";
- char *workbuf = (char *) alloca (sizeof (usrlibdebug)
- + (cp - realname)
- + strlen (debuginfo_fname));
- strcpy (stpcpy (workbuf, realname), debuginfo_fname);
-
- int fd2 = open (workbuf, O_RDONLY);
- if (fd2 == -1)
- {
- strcpy (stpcpy (stpcpy (workbuf, realname), ".debug/"),
- debuginfo_fname);
- fd2 = open (workbuf, O_RDONLY);
- if (fd2 == -1)
- {
- strcpy (stpcpy (stpcpy (workbuf, usrlibdebug), realname),
- debuginfo_fname);
- fd2 = open (workbuf, O_RDONLY);
- }
- }
-
- if (fd2 != -1)
- {
- ElfW(Ehdr) ehdr2;
-
- /* Read the ELF header. */
- if (pread (fd2, &ehdr2, sizeof (ehdr2), 0) != sizeof (ehdr2))
- error (EXIT_FAILURE, errno,
- _("reading of ELF header failed"));
-
- /* Map the section header. */
- size_t size = ehdr2.e_shnum * sizeof (ElfW(Shdr));
- ElfW(Shdr) *shdr2 = (ElfW(Shdr) *) alloca (size);
- if (pread (fd2, shdr2, size, ehdr2.e_shoff) != size)
- error (EXIT_FAILURE, errno,
- _("reading of section headers failed"));
-
- /* Get the section header string table. */
- shstrtab = (char *) alloca (shdr2[ehdr2.e_shstrndx].sh_size);
- if (pread (fd2, shstrtab, shdr2[ehdr2.e_shstrndx].sh_size,
- shdr2[ehdr2.e_shstrndx].sh_offset)
- != shdr2[ehdr2.e_shstrndx].sh_size)
- error (EXIT_FAILURE, errno,
- _("reading of section header string table failed"));
-
- /* Search for the ".symtab" section. */
- for (int idx = 0; idx < ehdr2.e_shnum; ++idx)
- if (shdr2[idx].sh_type == SHT_SYMTAB
- && strcmp (shstrtab + shdr2[idx].sh_name, ".symtab") == 0)
- {
- symtab_entry = &shdr2[idx];
- shdr = shdr2;
- symfd = fd2;
- break;
- }
-
- if (fd2 != symfd)
- close (fd2);
- }
- }
-
- no_debuginfo:
- if (symtab_entry == NULL)
- {
- fprintf (stderr, _("\
-*** The file `%s' is stripped: no detailed analysis possible\n"),
- name);
- result->symtab = NULL;
- result->strtab = NULL;
- }
- else
- {
- ElfW(Off) min_offset, max_offset;
- ElfW(Shdr) *strtab_entry;
-
- strtab_entry = &shdr[symtab_entry->sh_link];
-
- /* Find the minimum and maximum offsets that include both the symbol
- table and the string table. */
- if (symtab_entry->sh_offset < strtab_entry->sh_offset)
- {
- min_offset = symtab_entry->sh_offset & ~(pagesize - 1);
- max_offset = strtab_entry->sh_offset + strtab_entry->sh_size;
- }
- else
- {
- min_offset = strtab_entry->sh_offset & ~(pagesize - 1);
- max_offset = symtab_entry->sh_offset + symtab_entry->sh_size;
- }
-
- result->symbol_map = mmap (NULL, max_offset - min_offset,
- PROT_READ, MAP_SHARED|MAP_FILE, symfd,
- min_offset);
- if (result->symbol_map == MAP_FAILED)
- error (EXIT_FAILURE, errno, _("failed to load symbol data"));
-
- result->symtab
- = (const ElfW(Sym) *) ((const char *) result->symbol_map
- + (symtab_entry->sh_offset - min_offset));
- result->symtab_size = symtab_entry->sh_size;
- result->strtab = ((const char *) result->symbol_map
- + (strtab_entry->sh_offset - min_offset));
- result->symbol_mapsize = max_offset - min_offset;
- }
-
- /* Free the descriptor for the shared object. */
- close (fd);
- if (symfd != fd)
- close (symfd);
-
- return result;
-}
-
-
-static void
-unload_shobj (struct shobj *shobj)
-{
- munmap (shobj->symbol_map, shobj->symbol_mapsize);
- dlclose (shobj->map);
-}
-
-
-static struct profdata *
-load_profdata (const char *name, struct shobj *shobj)
-{
- struct profdata *result;
- int fd;
- struct stat64 st;
- void *addr;
- uint32_t *narcsp;
- size_t fromlimit;
- struct here_cg_arc_record *data;
- struct here_fromstruct *froms;
- uint16_t *tos;
- size_t fromidx;
- size_t idx;
-
- fd = open (name, O_RDONLY);
- if (fd == -1)
- {
- char *ext_name;
-
- if (errno != ENOENT || strchr (name, '/') != NULL)
- /* The file exists but we are not allowed to read it or the
- file does not exist and the name includes a path
- specification.. */
- return NULL;
-
- /* A file with the given name does not exist in the current
- directory, try it in the default location where the profiling
- files are created. */
- ext_name = (char *) alloca (strlen (name) + sizeof "/var/tmp/");
- stpcpy (stpcpy (ext_name, "/var/tmp/"), name);
- name = ext_name;
-
- fd = open (ext_name, O_RDONLY);
- if (fd == -1)
- {
- /* Even this file does not exist. */
- error (0, errno, _("cannot load profiling data"));
- return NULL;
- }
- }
-
- /* We have found the file, now make sure it is the right one for the
- data file. */
- if (fstat64 (fd, &st) < 0)
- {
- error (0, errno, _("while stat'ing profiling data file"));
- close (fd);
- return NULL;
- }
-
- if ((size_t) st.st_size != shobj->expected_size)
- {
- error (0, 0,
- _("profiling data file `%s' does not match shared object `%s'"),
- name, shobj->name);
- close (fd);
- return NULL;
- }
-
- /* The data file is most probably the right one for our shared
- object. Map it now. */
- addr = mmap (NULL, st.st_size, PROT_READ, MAP_SHARED|MAP_FILE, fd, 0);
- if (addr == MAP_FAILED)
- {
- error (0, errno, _("failed to mmap the profiling data file"));
- close (fd);
- return NULL;
- }
-
- /* We don't need the file desriptor anymore. */
- if (close (fd) < 0)
- {
- error (0, errno, _("error while closing the profiling data file"));
- munmap (addr, st.st_size);
- return NULL;
- }
-
- /* Prepare the result. */
- result = (struct profdata *) calloc (1, sizeof (struct profdata));
- if (result == NULL)
- {
- error (0, errno, _("cannot create internal descriptor"));
- munmap (addr, st.st_size);
- return NULL;
- }
-
- /* Store the address and size so that we can later free the resources. */
- result->addr = addr;
- result->size = st.st_size;
-
- /* Pointer to data after the header. */
- result->hist = (char *) ((struct gmon_hdr *) addr + 1);
- result->hist_hdr = (struct real_gmon_hist_hdr *) ((char *) result->hist
- + sizeof (uint32_t));
- result->kcount = (uint16_t *) ((char *) result->hist + sizeof (uint32_t)
- + sizeof (struct real_gmon_hist_hdr));
-
- /* Compute pointer to array of the arc information. */
- narcsp = (uint32_t *) ((char *) result->kcount + shobj->kcountsize
- + sizeof (uint32_t));
- result->narcs = *narcsp;
- result->data = (struct here_cg_arc_record *) ((char *) narcsp
- + sizeof (uint32_t));
-
- /* Create the gmon_hdr we expect or write. */
- struct real_gmon_hdr
- {
- char cookie[4];
- int32_t version;
- char spare[3 * 4];
- } gmon_hdr;
- if (sizeof (gmon_hdr) != sizeof (struct gmon_hdr)
- || (offsetof (struct real_gmon_hdr, cookie)
- != offsetof (struct gmon_hdr, cookie))
- || (offsetof (struct real_gmon_hdr, version)
- != offsetof (struct gmon_hdr, version)))
- abort ();
-
- memcpy (&gmon_hdr.cookie[0], GMON_MAGIC, sizeof (gmon_hdr.cookie));
- gmon_hdr.version = GMON_SHOBJ_VERSION;
- memset (gmon_hdr.spare, '\0', sizeof (gmon_hdr.spare));
-
- /* Create the hist_hdr we expect or write. */
- struct real_gmon_hist_hdr hist_hdr;
- if (sizeof (hist_hdr) != sizeof (struct gmon_hist_hdr)
- || (offsetof (struct real_gmon_hist_hdr, low_pc)
- != offsetof (struct gmon_hist_hdr, low_pc))
- || (offsetof (struct real_gmon_hist_hdr, high_pc)
- != offsetof (struct gmon_hist_hdr, high_pc))
- || (offsetof (struct real_gmon_hist_hdr, hist_size)
- != offsetof (struct gmon_hist_hdr, hist_size))
- || (offsetof (struct real_gmon_hist_hdr, prof_rate)
- != offsetof (struct gmon_hist_hdr, prof_rate))
- || (offsetof (struct real_gmon_hist_hdr, dimen)
- != offsetof (struct gmon_hist_hdr, dimen))
- || (offsetof (struct real_gmon_hist_hdr, dimen_abbrev)
- != offsetof (struct gmon_hist_hdr, dimen_abbrev)))
- abort ();
-
- hist_hdr.low_pc = (char *) shobj->lowpc - shobj->map->l_addr;
- hist_hdr.high_pc = (char *) shobj->highpc - shobj->map->l_addr;
- if (do_test)
- printf ("low_pc = %p\nhigh_pc = %p\n", hist_hdr.low_pc, hist_hdr.high_pc);
- hist_hdr.hist_size = shobj->kcountsize / sizeof (HISTCOUNTER);
- hist_hdr.prof_rate = __profile_frequency ();
- strncpy (hist_hdr.dimen, "seconds", sizeof (hist_hdr.dimen));
- hist_hdr.dimen_abbrev = 's';
-
- /* Test whether the header of the profiling data is ok. */
- if (memcmp (addr, &gmon_hdr, sizeof (struct gmon_hdr)) != 0
- || *(uint32_t *) result->hist != GMON_TAG_TIME_HIST
- || memcmp (result->hist_hdr, &hist_hdr,
- sizeof (struct gmon_hist_hdr)) != 0
- || narcsp[-1] != GMON_TAG_CG_ARC)
- {
- error (0, 0, _("`%s' is no correct profile data file for `%s'"),
- name, shobj->name);
- if (do_test)
- {
- if (memcmp (addr, &gmon_hdr, sizeof (struct gmon_hdr)) != 0)
- puts ("gmon_hdr differs");
- if (*(uint32_t *) result->hist != GMON_TAG_TIME_HIST)
- puts ("result->hist differs");
- if (memcmp (result->hist_hdr, &hist_hdr,
- sizeof (struct gmon_hist_hdr)) != 0)
- puts ("hist_hdr differs");
- if (narcsp[-1] != GMON_TAG_CG_ARC)
- puts ("narcsp[-1] differs");
- }
- free (result);
- munmap (addr, st.st_size);
- return NULL;
- }
-
- /* We are pretty sure now that this is a correct input file. Set up
- the remaining information in the result structure and return. */
- result->tos = (uint16_t *) calloc (shobj->tossize + shobj->fromssize, 1);
- if (result->tos == NULL)
- {
- error (0, errno, _("cannot create internal descriptor"));
- munmap (addr, st.st_size);
- free (result);
- return NULL;
- }
-
- result->froms = (struct here_fromstruct *) ((char *) result->tos
- + shobj->tossize);
- fromidx = 0;
-
- /* Now we have to process all the arc count entries. */
- fromlimit = shobj->fromlimit;
- data = result->data;
- froms = result->froms;
- tos = result->tos;
- for (idx = 0; idx < MIN (*narcsp, fromlimit); ++idx)
- {
- size_t to_index;
- size_t newfromidx;
- to_index = (data[idx].self_pc / (shobj->hashfraction * sizeof (*tos)));
- newfromidx = fromidx++;
- froms[newfromidx].here = &data[idx];
- froms[newfromidx].link = tos[to_index];
- tos[to_index] = newfromidx;
- }
-
- return result;
-}
-
-
-static void
-unload_profdata (struct profdata *profdata)
-{
- free (profdata->tos);
- munmap (profdata->addr, profdata->size);
- free (profdata);
-}
-
-
-static void
-count_total_ticks (struct shobj *shobj, struct profdata *profdata)
-{
- volatile uint16_t *kcount = profdata->kcount;
- size_t maxkidx = shobj->kcountsize;
- size_t factor = 2 * (65536 / shobj->s_scale);
- size_t kidx = 0;
- size_t sidx = 0;
-
- while (sidx < symidx)
- {
- uintptr_t start = sortsym[sidx]->addr;
- uintptr_t end = start + sortsym[sidx]->size;
-
- while (kidx < maxkidx && factor * kidx < start)
- ++kidx;
- if (kidx == maxkidx)
- break;
-
- while (kidx < maxkidx && factor * kidx < end)
- sortsym[sidx]->ticks += kcount[kidx++];
- if (kidx == maxkidx)
- break;
-
- total_ticks += sortsym[sidx++]->ticks;
- }
-}
-
-
-static size_t
-find_symbol (uintptr_t addr)
-{
- size_t sidx = 0;
-
- while (sidx < symidx)
- {
- uintptr_t start = sortsym[sidx]->addr;
- uintptr_t end = start + sortsym[sidx]->size;
-
- if (addr >= start && addr < end)
- return sidx;
-
- if (addr < start)
- break;
-
- ++sidx;
- }
-
- return (size_t) -1l;
-}
-
-
-static void
-count_calls (struct shobj *shobj, struct profdata *profdata)
-{
- struct here_cg_arc_record *data = profdata->data;
- uint32_t narcs = profdata->narcs;
- uint32_t cnt;
-
- for (cnt = 0; cnt < narcs; ++cnt)
- {
- uintptr_t here = data[cnt].self_pc;
- size_t symbol_idx;
-
- /* Find the symbol for this address. */
- symbol_idx = find_symbol (here);
- if (symbol_idx != (size_t) -1l)
- sortsym[symbol_idx]->calls += data[cnt].count;
- }
-}
-
-
-static int
-symorder (const void *o1, const void *o2)
-{
- const struct known_symbol *p1 = (const struct known_symbol *) o1;
- const struct known_symbol *p2 = (const struct known_symbol *) o2;
-
- return p1->addr - p2->addr;
-}
-
-
-static void
-printsym (const void *node, VISIT value, int level)
-{
- if (value == leaf || value == postorder)
- sortsym[symidx++] = *(struct known_symbol **) node;
-}
-
-
-static void
-read_symbols (struct shobj *shobj)
-{
- int n = 0;
-
- /* Initialize the obstacks. */
-#define obstack_chunk_alloc malloc
-#define obstack_chunk_free free
- obstack_init (&shobj->ob_str);
- obstack_init (&shobj->ob_sym);
- obstack_init (&ob_list);
-
- /* Process the symbols. */
- if (shobj->symtab != NULL)
- {
- const ElfW(Sym) *sym = shobj->symtab;
- const ElfW(Sym) *sym_end
- = (const ElfW(Sym) *) ((const char *) sym + shobj->symtab_size);
- for (; sym < sym_end; sym++)
- if ((ELFW(ST_TYPE) (sym->st_info) == STT_FUNC
- || ELFW(ST_TYPE) (sym->st_info) == STT_NOTYPE)
- && sym->st_size != 0)
- {
- struct known_symbol **existp;
- struct known_symbol *newsym
- = (struct known_symbol *) obstack_alloc (&shobj->ob_sym,
- sizeof (*newsym));
- if (newsym == NULL)
- error (EXIT_FAILURE, errno, _("cannot allocate symbol data"));
-
- newsym->name = &shobj->strtab[sym->st_name];
- newsym->addr = sym->st_value;
- newsym->size = sym->st_size;
- newsym->weak = ELFW(ST_BIND) (sym->st_info) == STB_WEAK;
- newsym->hidden = (ELFW(ST_VISIBILITY) (sym->st_other)
- != STV_DEFAULT);
- newsym->ticks = 0;
- newsym->calls = 0;
-
- existp = tfind (newsym, &symroot, symorder);
- if (existp == NULL)
- {
- /* New function. */
- tsearch (newsym, &symroot, symorder);
- ++n;
- }
- else
- {
- /* The function is already defined. See whether we have
- a better name here. */
- if (((*existp)->hidden && !newsym->hidden)
- || ((*existp)->name[0] == '_' && newsym->name[0] != '_')
- || ((*existp)->name[0] != '_' && newsym->name[0] != '_'
- && ((*existp)->weak && !newsym->weak)))
- *existp = newsym;
- else
- /* We don't need the allocated memory. */
- obstack_free (&shobj->ob_sym, newsym);
- }
- }
- }
- else
- {
- /* Blarg, the binary is stripped. We have to rely on the
- information contained in the dynamic section of the object. */
- const ElfW(Sym) *symtab = (ElfW(Sym) *) D_PTR (shobj->map,
- l_info[DT_SYMTAB]);
- const char *strtab = (const char *) D_PTR (shobj->map,
- l_info[DT_STRTAB]);
-
- /* We assume that the string table follows the symbol table,
- because there is no way in ELF to know the size of the
- dynamic symbol table without looking at the section headers. */
- while ((void *) symtab < (void *) strtab)
- {
- if ((ELFW(ST_TYPE)(symtab->st_info) == STT_FUNC
- || ELFW(ST_TYPE)(symtab->st_info) == STT_NOTYPE)
- && symtab->st_size != 0)
- {
- struct known_symbol *newsym;
- struct known_symbol **existp;
-
- newsym =
- (struct known_symbol *) obstack_alloc (&shobj->ob_sym,
- sizeof (*newsym));
- if (newsym == NULL)
- error (EXIT_FAILURE, errno, _("cannot allocate symbol data"));
-
- newsym->name = &strtab[symtab->st_name];
- newsym->addr = symtab->st_value;
- newsym->size = symtab->st_size;
- newsym->weak = ELFW(ST_BIND) (symtab->st_info) == STB_WEAK;
- newsym->hidden = (ELFW(ST_VISIBILITY) (symtab->st_other)
- != STV_DEFAULT);
- newsym->ticks = 0;
- newsym->froms = NULL;
- newsym->tos = NULL;
-
- existp = tfind (newsym, &symroot, symorder);
- if (existp == NULL)
- {
- /* New function. */
- tsearch (newsym, &symroot, symorder);
- ++n;
- }
- else
- {
- /* The function is already defined. See whether we have
- a better name here. */
- if (((*existp)->hidden && !newsym->hidden)
- || ((*existp)->name[0] == '_' && newsym->name[0] != '_')
- || ((*existp)->name[0] != '_' && newsym->name[0] != '_'
- && ((*existp)->weak && !newsym->weak)))
- *existp = newsym;
- else
- /* We don't need the allocated memory. */
- obstack_free (&shobj->ob_sym, newsym);
- }
- }
-
- ++symtab;
- }
- }
-
- sortsym = malloc (n * sizeof (struct known_symbol *));
- if (sortsym == NULL)
- abort ();
-
- twalk (symroot, printsym);
-}
-
-
-static void
-add_arcs (struct profdata *profdata)
-{
- uint32_t narcs = profdata->narcs;
- struct here_cg_arc_record *data = profdata->data;
- uint32_t cnt;
-
- for (cnt = 0; cnt < narcs; ++cnt)
- {
- /* First add the incoming arc. */
- size_t sym_idx = find_symbol (data[cnt].self_pc);
-
- if (sym_idx != (size_t) -1l)
- {
- struct known_symbol *sym = sortsym[sym_idx];
- struct arc_list *runp = sym->froms;
-
- while (runp != NULL
- && ((data[cnt].from_pc == 0 && runp->idx != (size_t) -1l)
- || (data[cnt].from_pc != 0
- && (runp->idx == (size_t) -1l
- || data[cnt].from_pc < sortsym[runp->idx]->addr
- || (data[cnt].from_pc
- >= (sortsym[runp->idx]->addr
- + sortsym[runp->idx]->size))))))
- runp = runp->next;
-
- if (runp == NULL)
- {
- /* We need a new entry. */
- struct arc_list *newp = (struct arc_list *)
- obstack_alloc (&ob_list, sizeof (struct arc_list));
-
- if (data[cnt].from_pc == 0)
- newp->idx = (size_t) -1l;
- else
- newp->idx = find_symbol (data[cnt].from_pc);
- newp->count = data[cnt].count;
- newp->next = sym->froms;
- sym->froms = newp;
- }
- else
- /* Increment the counter for the found entry. */
- runp->count += data[cnt].count;
- }
-
- /* Now add it to the appropriate outgoing list. */
- sym_idx = find_symbol (data[cnt].from_pc);
- if (sym_idx != (size_t) -1l)
- {
- struct known_symbol *sym = sortsym[sym_idx];
- struct arc_list *runp = sym->tos;
-
- while (runp != NULL
- && (runp->idx == (size_t) -1l
- || data[cnt].self_pc < sortsym[runp->idx]->addr
- || data[cnt].self_pc >= (sortsym[runp->idx]->addr
- + sortsym[runp->idx]->size)))
- runp = runp->next;
-
- if (runp == NULL)
- {
- /* We need a new entry. */
- struct arc_list *newp = (struct arc_list *)
- obstack_alloc (&ob_list, sizeof (struct arc_list));
-
- newp->idx = find_symbol (data[cnt].self_pc);
- newp->count = data[cnt].count;
- newp->next = sym->tos;
- sym->tos = newp;
- }
- else
- /* Increment the counter for the found entry. */
- runp->count += data[cnt].count;
- }
- }
-}
-
-
-static int
-countorder (const void *p1, const void *p2)
-{
- struct known_symbol *s1 = (struct known_symbol *) p1;
- struct known_symbol *s2 = (struct known_symbol *) p2;
-
- if (s1->ticks != s2->ticks)
- return (int) (s2->ticks - s1->ticks);
-
- if (s1->calls != s2->calls)
- return (int) (s2->calls - s1->calls);
-
- return strcmp (s1->name, s2->name);
-}
-
-
-static double tick_unit;
-static uintmax_t cumu_ticks;
-
-static void
-printflat (const void *node, VISIT value, int level)
-{
- if (value == leaf || value == postorder)
- {
- struct known_symbol *s = *(struct known_symbol **) node;
-
- cumu_ticks += s->ticks;
-
- printf ("%6.2f%10.2f%9.2f%9" PRIdMAX "%9.2f %s\n",
- total_ticks ? (100.0 * s->ticks) / total_ticks : 0.0,
- tick_unit * cumu_ticks,
- tick_unit * s->ticks,
- s->calls,
- s->calls ? (s->ticks * 1000000) * tick_unit / s->calls : 0,
- /* FIXME: don't know about called functions. */
- s->name);
- }
-}
-
-
-/* ARGUSED */
-static void
-freenoop (void *p)
-{
-}
-
-
-static void
-generate_flat_profile (struct profdata *profdata)
-{
- size_t n;
- void *data = NULL;
-
- tick_unit = 1.0 / profdata->hist_hdr->prof_rate;
-
- printf ("Flat profile:\n\n"
- "Each sample counts as %g %s.\n",
- tick_unit, profdata->hist_hdr->dimen);
- fputs (" % cumulative self self total\n"
- " time seconds seconds calls us/call us/call name\n",
- stdout);
-
- for (n = 0; n < symidx; ++n)
- if (sortsym[n]->calls != 0 || sortsym[n]->ticks != 0)
- tsearch (sortsym[n], &data, countorder);
-
- twalk (data, printflat);
-
- tdestroy (data, freenoop);
-}
-
-
-static void
-generate_call_graph (struct profdata *profdata)
-{
- size_t cnt;
-
- puts ("\nindex % time self children called name\n");
-
- for (cnt = 0; cnt < symidx; ++cnt)
- if (sortsym[cnt]->froms != NULL || sortsym[cnt]->tos != NULL)
- {
- struct arc_list *runp;
- size_t n;
-
- /* First print the from-information. */
- runp = sortsym[cnt]->froms;
- while (runp != NULL)
- {
- printf (" %8.2f%8.2f%9" PRIdMAX "/%-9" PRIdMAX " %s",
- (runp->idx != (size_t) -1l
- ? sortsym[runp->idx]->ticks * tick_unit : 0.0),
- 0.0, /* FIXME: what's time for the children, recursive */
- runp->count, sortsym[cnt]->calls,
- (runp->idx != (size_t) -1l ?
- sortsym[runp->idx]->name : "<UNKNOWN>"));
-
- if (runp->idx != (size_t) -1l)
- printf (" [%Zd]", runp->idx);
- putchar_unlocked ('\n');
-
- runp = runp->next;
- }
-
- /* Info about the function itself. */
- n = printf ("[%Zu]", cnt);
- printf ("%*s%5.1f%8.2f%8.2f%9" PRIdMAX " %s [%Zd]\n",
- (int) (7 - n), " ",
- total_ticks ? (100.0 * sortsym[cnt]->ticks) / total_ticks : 0,
- sortsym[cnt]->ticks * tick_unit,
- 0.0, /* FIXME: what's time for the children, recursive */
- sortsym[cnt]->calls,
- sortsym[cnt]->name, cnt);
-
- /* Info about the functions this function calls. */
- runp = sortsym[cnt]->tos;
- while (runp != NULL)
- {
- printf (" %8.2f%8.2f%9" PRIdMAX "/",
- (runp->idx != (size_t) -1l
- ? sortsym[runp->idx]->ticks * tick_unit : 0.0),
- 0.0, /* FIXME: what's time for the children, recursive */
- runp->count);
-
- if (runp->idx != (size_t) -1l)
- printf ("%-9" PRIdMAX " %s [%Zd]\n",
- sortsym[runp->idx]->calls,
- sortsym[runp->idx]->name,
- runp->idx);
- else
- fputs ("??? <UNKNOWN>\n\n", stdout);
-
- runp = runp->next;
- }
-
- fputs ("-----------------------------------------------\n", stdout);
- }
-}
-
-
-static void
-generate_call_pair_list (struct profdata *profdata)
-{
- size_t cnt;
-
- for (cnt = 0; cnt < symidx; ++cnt)
- if (sortsym[cnt]->froms != NULL || sortsym[cnt]->tos != NULL)
- {
- struct arc_list *runp;
-
- /* First print the incoming arcs. */
- runp = sortsym[cnt]->froms;
- while (runp != NULL)
- {
- if (runp->idx == (size_t) -1l)
- printf ("\
-<UNKNOWN> %-34s %9" PRIdMAX "\n",
- sortsym[cnt]->name, runp->count);
- runp = runp->next;
- }
-
- /* Next the outgoing arcs. */
- runp = sortsym[cnt]->tos;
- while (runp != NULL)
- {
- printf ("%-34s %-34s %9" PRIdMAX "\n",
- sortsym[cnt]->name,
- (runp->idx != (size_t) -1l
- ? sortsym[runp->idx]->name : "<UNKNOWN>"),
- runp->count);
- runp = runp->next;
- }
- }
-}
diff --git a/elf/static-stubs.c b/elf/static-stubs.c
deleted file mode 100644
index f81d5b792b..0000000000
--- a/elf/static-stubs.c
+++ /dev/null
@@ -1,46 +0,0 @@
-/* Stub implementations of functions to link into statically linked
- programs without needing libgcc_eh.
- Copyright (C) 2012-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Avoid backtrace (and so _Unwind_Backtrace) dependencies from
- sysdeps/unix/sysv/linux/libc_fatal.c. */
-#include <sysdeps/posix/libc_fatal.c>
-
-#include <stdlib.h>
-#include <unwind.h>
-
-/* These programs do not use thread cancellation, so _Unwind_Resume
- and the personality routine are never actually called. */
-
-void
-_Unwind_Resume (struct _Unwind_Exception *exc __attribute__ ((unused)))
-{
- abort ();
-}
-
-_Unwind_Reason_Code
-__gcc_personality_v0 (int version __attribute__ ((unused)),
- _Unwind_Action actions __attribute__ ((unused)),
- _Unwind_Exception_Class exception_class
- __attribute__ ((unused)),
- struct _Unwind_Exception *ue_header
- __attribute__ ((unused)),
- struct _Unwind_Context *context __attribute__ ((unused)))
-{
- abort ();
-}
diff --git a/elf/testobj.h b/elf/testobj.h
deleted file mode 100644
index 1707ae340e..0000000000
--- a/elf/testobj.h
+++ /dev/null
@@ -1,28 +0,0 @@
-extern int preload (int a);
-
-extern int foo (int);
-
-extern int obj1func1 (int);
-
-extern int obj1func2 (int);
-
-extern int obj2func1 (int);
-
-extern int obj2func2 (int);
-
-extern int obj3func1 (int);
-
-extern int obj3func2 (int);
-
-extern int obj4func1 (int);
-
-extern int obj4func2 (int);
-
-extern int obj5func1 (int);
-
-extern int obj5func2 (int);
-
-extern int obj6func1 (int);
-
-extern int obj6func2 (int);
-
diff --git a/elf/testobj1.c b/elf/testobj1.c
deleted file mode 100644
index 5ab20efd62..0000000000
--- a/elf/testobj1.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-
-#include "testobj.h"
-
-int
-obj1func1 (int a __attribute__ ((unused)))
-{
- return 42;
-}
-
-int
-obj1func2 (int a)
-{
- return foo (a) + 10;
-}
-
-int
-preload (int a)
-{
- int (*fp) (int) = dlsym (RTLD_NEXT, "preload");
- if (fp != NULL)
- return fp (a) + 10;
- return 10;
-}
diff --git a/elf/testobj1_1.c b/elf/testobj1_1.c
deleted file mode 100644
index 2541a5ad1b..0000000000
--- a/elf/testobj1_1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-#include "testobj.h"
-
-int
-obj1func1 (int a)
-{
- return 42 + obj1func2 (a);
-}
diff --git a/elf/testobj2.c b/elf/testobj2.c
deleted file mode 100644
index 7e4b610982..0000000000
--- a/elf/testobj2.c
+++ /dev/null
@@ -1,32 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-#include "testobj.h"
-
-int
-obj2func1 (int a __attribute__ ((unused)))
-{
- return 43;
-}
-
-int
-obj2func2 (int a)
-{
- return obj1func1 (a) + 10;
-}
-
-int
-preload (int a)
-{
- int (*fp) (int) = dlsym (RTLD_NEXT, "preload");
- if (fp != NULL)
- return fp (a) + 10;
- return 10;
-}
-
-void
-p (void)
-{
- puts ("hello world");
-}
diff --git a/elf/testobj3.c b/elf/testobj3.c
deleted file mode 100644
index c025ff631a..0000000000
--- a/elf/testobj3.c
+++ /dev/null
@@ -1,26 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-
-#include "testobj.h"
-
-
-int
-obj3func1 (int a __attribute__ ((unused)))
-{
- return 44;
-}
-
-int
-obj3func2 (int a)
-{
- return foo (a) + 42;
-}
-
-int
-preload (int a)
-{
- int (*fp) (int) = dlsym (RTLD_NEXT, "preload");
- if (fp != NULL)
- return fp (a) + 10;
- return 10;
-}
diff --git a/elf/testobj4.c b/elf/testobj4.c
deleted file mode 100644
index 2729ba32be..0000000000
--- a/elf/testobj4.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-
-#include "testobj.h"
-
-int
-obj4func1 (int a __attribute__ ((unused)))
-{
- return 55;
-}
-
-int
-obj4func2 (int a)
-{
- return foo (a) + 43;
-}
-
-int
-preload (int a)
-{
- int (*fp) (int) = dlsym (RTLD_NEXT, "preload");
- if (fp != NULL)
- return fp (a) + 10;
- return 10;
-}
diff --git a/elf/testobj5.c b/elf/testobj5.c
deleted file mode 100644
index 9675cad88d..0000000000
--- a/elf/testobj5.c
+++ /dev/null
@@ -1,26 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-
-#include "testobj.h"
-
-
-int
-obj5func1 (int a __attribute__ ((unused)))
-{
- return 66;
-}
-
-int
-obj5func2 (int a)
-{
- return foo (a) + 44;
-}
-
-int
-preload (int a)
-{
- int (*fp) (int) = dlsym (RTLD_NEXT, "preload");
- if (fp != NULL)
- return fp (a) + 10;
- return 10;
-}
diff --git a/elf/testobj6.c b/elf/testobj6.c
deleted file mode 100644
index fcba01631d..0000000000
--- a/elf/testobj6.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include "testobj.h"
-
-int
-obj6func1 (int a __attribute__ ((unused)))
-{
- return 77;
-}
-
-int
-obj6func2 (int a)
-{
- return foo (a) + 46;
-}
-
-int
-preload (int a)
-{
- return a;
-}
diff --git a/elf/tls-macros.h b/elf/tls-macros.h
deleted file mode 100644
index e25e33b0f0..0000000000
--- a/elf/tls-macros.h
+++ /dev/null
@@ -1,25 +0,0 @@
-/* Macros to support TLS testing in times of missing compiler support. */
-
-#define COMMON_INT_DEF(x) \
- asm (".tls_common " #x ",4,4")
-/* XXX Until we get compiler support we don't need declarations. */
-#define COMMON_INT_DECL(x)
-
-/* XXX This definition will probably be machine specific, too. */
-#define VAR_INT_DEF(x) \
- asm (".section .tdata\n\t" \
- ".globl " #x "\n" \
- ".balign 4\n" \
- #x ":\t.long 0\n\t" \
- ".size " #x ",4\n\t" \
- ".previous")
-/* XXX Until we get compiler support we don't need declarations. */
-#define VAR_INT_DECL(x)
-
-#include_next <tls-macros.h>
-
- /* XXX Each architecture must have its own asm for now. */
-#if !defined TLS_LE || !defined TLS_IE \
- || !defined TLS_LD || !defined TLS_GD
-# error "No support for this architecture so far."
-#endif
diff --git a/elf/tlsdeschtab.h b/elf/tlsdeschtab.h
deleted file mode 100644
index 3091d8b420..0000000000
--- a/elf/tlsdeschtab.h
+++ /dev/null
@@ -1,164 +0,0 @@
-/* Hash table for TLS descriptors.
- Copyright (C) 2005-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Alexandre Oliva <aoliva@redhat.com>
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef TLSDESCHTAB_H
-# define TLSDESCHTAB_H 1
-
-#include <atomic.h>
-
-# ifdef SHARED
-
-# include <inline-hashtab.h>
-
-inline static int
-hash_tlsdesc (void *p)
-{
- struct tlsdesc_dynamic_arg *td = p;
-
- /* We know all entries are for the same module, so ti_offset is the
- only distinguishing entry. */
- return td->tlsinfo.ti_offset;
-}
-
-inline static int
-eq_tlsdesc (void *p, void *q)
-{
- struct tlsdesc_dynamic_arg *tdp = p, *tdq = q;
-
- return tdp->tlsinfo.ti_offset == tdq->tlsinfo.ti_offset;
-}
-
-inline static size_t
-map_generation (struct link_map *map)
-{
- size_t idx = map->l_tls_modid;
- struct dtv_slotinfo_list *listp = GL(dl_tls_dtv_slotinfo_list);
-
- /* Find the place in the dtv slotinfo list. */
- do
- {
- /* Does it fit in the array of this list element? */
- if (idx < listp->len)
- {
- /* We should never get here for a module in static TLS, so
- we can assume that, if the generation count is zero, we
- still haven't determined the generation count for this
- module. */
- if (listp->slotinfo[idx].map == map && listp->slotinfo[idx].gen)
- return listp->slotinfo[idx].gen;
- else
- break;
- }
- idx -= listp->len;
- listp = listp->next;
- }
- while (listp != NULL);
-
- /* If we get to this point, the module still hasn't been assigned an
- entry in the dtv slotinfo data structures, and it will when we're
- done with relocations. At that point, the module will get a
- generation number that is one past the current generation, so
- return exactly that. */
- return GL(dl_tls_generation) + 1;
-}
-
-void *
-internal_function
-_dl_make_tlsdesc_dynamic (struct link_map *map, size_t ti_offset)
-{
- struct hashtab *ht;
- void **entry;
- struct tlsdesc_dynamic_arg *td, test;
-
- /* FIXME: We could use a per-map lock here, but is it worth it? */
- __rtld_lock_lock_recursive (GL(dl_load_lock));
-
- ht = map->l_mach.tlsdesc_table;
- if (! ht)
- {
- ht = htab_create ();
- if (! ht)
- {
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return 0;
- }
- map->l_mach.tlsdesc_table = ht;
- }
-
- test.tlsinfo.ti_module = map->l_tls_modid;
- test.tlsinfo.ti_offset = ti_offset;
- entry = htab_find_slot (ht, &test, 1, hash_tlsdesc, eq_tlsdesc);
- if (! entry)
- {
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return 0;
- }
-
- if (*entry)
- {
- td = *entry;
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return td;
- }
-
- *entry = td = malloc (sizeof (struct tlsdesc_dynamic_arg));
- /* This may be higher than the map's generation, but it doesn't
- matter much. Worst case, we'll have one extra DTV update per
- thread. */
- td->gen_count = map_generation (map);
- td->tlsinfo = test.tlsinfo;
-
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return td;
-}
-
-# endif /* SHARED */
-
-/* The idea of the following two functions is to stop multiple threads
- from attempting to resolve the same TLS descriptor without busy
- waiting. Ideally, we should be able to release the lock right
- after changing td->entry, and then using say a condition variable
- or a futex wake to wake up any waiting threads, but let's try to
- avoid introducing such dependencies. */
-
-static int
-_dl_tlsdesc_resolve_early_return_p (struct tlsdesc volatile *td, void *caller)
-{
- if (caller != atomic_load_relaxed (&td->entry))
- return 1;
-
- __rtld_lock_lock_recursive (GL(dl_load_lock));
- if (caller != atomic_load_relaxed (&td->entry))
- {
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
- return 1;
- }
-
- atomic_store_relaxed (&td->entry, _dl_tlsdesc_resolve_hold);
-
- return 0;
-}
-
-static void
-_dl_tlsdesc_wake_up_held_fixups (void)
-{
- __rtld_lock_unlock_recursive (GL(dl_load_lock));
-}
-
-#endif
diff --git a/elf/tst-_dl_addr_inside_object.c b/elf/tst-_dl_addr_inside_object.c
deleted file mode 100644
index 1604b8df63..0000000000
--- a/elf/tst-_dl_addr_inside_object.c
+++ /dev/null
@@ -1,222 +0,0 @@
-/* Unit test for _dl_addr_inside_object.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <link.h>
-#include <elf.h>
-#include <libc-symbols.h>
-
-extern int internal_function _dl_addr_inside_object (struct link_map *l,
- const ElfW(Addr) addr);
-
-static int
-do_test (void)
-{
- int ret, err = 0;
- ElfW(Addr) addr;
- struct link_map map;
- ElfW(Phdr) header;
- map.l_phdr = &header;
- map.l_phnum = 1;
- map.l_addr = 0x0;
- /* Segment spans 0x2000 -> 0x4000. */
- header.p_vaddr = 0x2000;
- header.p_memsz = 0x2000;
- header.p_type = PT_LOAD;
- /* Address is above the segment e.g. > 0x4000. */
- addr = 0x5000;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: Above: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: Above: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: Above: Invalid return value.\n");
- exit (1);
- }
- /* Address is inside the segment e.g. 0x2000 < addr < 0x4000. */
- addr = 0x3000;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("FAIL: Inside: Address is detected as outside the segment.\n");
- err++;
- break;
- case 1:
- printf ("PASS: Inside: Address is detected as inside the segment.\n");
- break;
- default:
- printf ("FAIL: Inside: Invalid return value.\n");
- exit (1);
- }
- /* Address is below the segment e.g. < 0x2000. */
- addr = 0x1000;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: Below: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: Below: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: Below: Invalid return value.\n");
- exit (1);
- }
- /* Address is in the segment and addr == p_vaddr. */
- addr = 0x2000;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("FAIL: At p_vaddr: Address is detected as outside the segment.\n");
- err++;
- break;
- case 1:
- printf ("PASS: At p_vaddr: Address is detected as inside the segment.\n");
- break;
- default:
- printf ("FAIL: At p_vaddr: Invalid return value.\n");
- exit (1);
- }
- /* Address is in the segment and addr == p_vaddr + p_memsz - 1. */
- addr = 0x2000 + 0x2000 - 0x1;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("FAIL: At p_memsz-1: Address is detected as outside the segment.\n");
- err++;
- break;
- case 1:
- printf ("PASS: At p_memsz-1: Address is detected as inside the segment.\n");
- break;
- default:
- printf ("FAIL: At p_memsz-1: Invalid return value.\n");
- exit (1);
- }
- /* Address is outside the segment and addr == p_vaddr + p_memsz. */
- addr = 0x2000 + 0x2000;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: At p_memsz: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: At p_memsz: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: At p_memsz: Invalid return value.\n");
- exit (1);
- }
- /* Address is outside the segment and p_vaddr at maximum address. */
- addr = 0x0 - 0x2;
- header.p_vaddr = 0x0 - 0x1;
- header.p_memsz = 0x1;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: At max: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: At max: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: At max: Invalid return value.\n");
- exit (1);
- }
- /* Address is outside the segment and p_vaddr at minimum address. */
- addr = 0x1;
- header.p_vaddr = 0x0;
- header.p_memsz = 0x1;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: At min: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: At min: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: At min: Invalid return value.\n");
- exit (1);
- }
- /* Address is always inside the segment with p_memsz at max. */
- addr = 0x0;
- header.p_vaddr = 0x0;
- header.p_memsz = 0x0 - 0x1;
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("FAIL: At maxmem: Address is detected as outside the segment.\n");
- err++;
- break;
- case 1:
- printf ("PASS: At maxmem: Address is detected as inside the segment.\n");
- break;
- default:
- printf ("FAIL: At maxmem: Invalid return value.\n");
- exit (1);
- }
- /* Attempt to wrap addr into the segment.
- Pick a load address in the middle of the address space.
- Place the test address at 0x0 so it wraps to the middle again. */
- map.l_addr = 0x0 - 0x1;
- map.l_addr = map.l_addr / 2;
- addr = 0;
- /* Setup a segment covering 1/2 the address space. */
- header.p_vaddr = 0x0;
- header.p_memsz = 0x0 - 0x1 - map.l_addr;
- /* No matter where you place addr everything is shifted modulo l_addr
- and even with this underflow you're always 1 byte away from being
- in the range. */
- ret = _dl_addr_inside_object (&map, addr);
- switch (ret)
- {
- case 0:
- printf ("PASS: Underflow: Address is detected as outside the segment.\n");
- break;
- case 1:
- printf ("FAIL: Underflow: Address is detected as inside the segment.\n");
- err++;
- break;
- default:
- printf ("FAIL: Underflow: Invalid return value.\n");
- exit (1);
- }
-
- return err;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-addr1.c b/elf/tst-addr1.c
deleted file mode 100644
index 68ff74aabd..0000000000
--- a/elf/tst-addr1.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <string.h>
-
-static int
-do_test (void)
-{
- Dl_info i;
- if (dladdr (&printf, &i) == 0)
- {
- puts ("not found");
- return 1;
- }
- printf ("found symbol %s in %s\n", i.dli_sname, i.dli_fname);
- return i.dli_sname == NULL
- || (strcmp (i.dli_sname, "printf") != 0
- /* On architectures which create PIC code by default
- &printf may resolve to an address in libc.so
- rather than in the binary. printf and _IO_printf
- are aliased and which one comes first in the
- hash table is up to the linker. */
- && strcmp (i.dli_sname, "_IO_printf") != 0);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-align.c b/elf/tst-align.c
deleted file mode 100644
index 01b0b4ffb3..0000000000
--- a/elf/tst-align.c
+++ /dev/null
@@ -1,52 +0,0 @@
-/* Copyright (C) 2003-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-alignmod.so";
- int result = 0;
- void (*fp) (int *);
- void *h;
-
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- fp = dlsym (h, "in_dso");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso': %s\n", dlerror ());
- exit (1);
- }
-
- fp (&result);
-
- dlclose (h);
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-align2.c b/elf/tst-align2.c
deleted file mode 100644
index 78b66be20a..0000000000
--- a/elf/tst-align2.c
+++ /dev/null
@@ -1,155 +0,0 @@
-/* Copyright (C) 2005-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2005.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <sys/wait.h>
-#include <tst-stack-align.h>
-#include <unistd.h>
-
-static int res, fds[2], result;
-static bool test_destructors;
-
-extern void in_dso (int *, bool *, int *);
-
-static void __attribute__ ((constructor)) con (void)
-{
- res = TEST_STACK_ALIGN () ? -1 : 1;
-}
-
-static void __attribute__ ((destructor)) des (void)
-{
- if (!test_destructors)
- return;
-
- char c = TEST_STACK_ALIGN () ? 'B' : 'A';
- write (fds[1], &c, 1);
-}
-
-static int
-do_test (void)
-{
- if (!res)
- {
- puts ("binary's constructor has not been run");
- result = 1;
- }
- else if (res != 1)
- {
- puts ("binary's constructor has been run without sufficient alignment");
- result = 1;
- }
-
- if (TEST_STACK_ALIGN ())
- {
- puts ("insufficient stack alignment in do_test");
- result = 1;
- }
-
- in_dso (&result, &test_destructors, &fds[1]);
-
- if (pipe (fds) < 0)
- {
- printf ("couldn't create pipe: %m\n");
- return 1;
- }
-
- pid_t pid = fork ();
- if (pid < 0)
- {
- printf ("fork failed: %m\n");
- return 1;
- }
-
- if (!pid)
- {
- close (fds[0]);
- test_destructors = true;
- exit (0);
- }
-
- close (fds[1]);
-
- unsigned char c;
- ssize_t len;
- int des_seen = 0, dso_des_seen = 0;
- while ((len = TEMP_FAILURE_RETRY (read (fds[0], &c, 1))) > 0)
- {
- switch (c)
- {
- case 'B':
- puts ("insufficient alignment in binary's destructor");
- result = 1;
- /* FALLTHROUGH */
- case 'A':
- des_seen++;
- break;
- case 'D':
- puts ("insufficient alignment in DSO destructor");
- result = 1;
- /* FALLTHROUGH */
- case 'C':
- dso_des_seen++;
- break;
- default:
- printf ("unexpected character %x read from pipe", c);
- result = 1;
- break;
- }
- }
-
- close (fds[0]);
-
- if (des_seen != 1)
- {
- printf ("binary destructor run %d times instead of once\n", des_seen);
- result = 1;
- }
-
- if (dso_des_seen != 1)
- {
- printf ("DSO destructor run %d times instead of once\n", dso_des_seen);
- result = 1;
- }
-
- int status;
- pid_t termpid;
- termpid = TEMP_FAILURE_RETRY (waitpid (pid, &status, 0));
- if (termpid == -1)
- {
- printf ("waitpid failed: %m\n");
- result = 1;
- }
- else if (termpid != pid)
- {
- printf ("waitpid returned %ld != %ld\n",
- (long int) termpid, (long int) pid);
- result = 1;
- }
- else if (!WIFEXITED (status) || WEXITSTATUS (status))
- {
- puts ("child hasn't exited with exit status 0");
- result = 1;
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-alignmod.c b/elf/tst-alignmod.c
deleted file mode 100644
index b5e47be0bd..0000000000
--- a/elf/tst-alignmod.c
+++ /dev/null
@@ -1,52 +0,0 @@
-/* Copyright (C) 2003-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdio.h>
-#include <tst-stack-align.h>
-
-static int res, *resp;
-
-static void __attribute__((constructor))
-con (void)
-{
- res = TEST_STACK_ALIGN () ? -1 : 1;
-}
-
-void
-in_dso (int *result)
-{
- if (!res)
- {
- puts ("constructor has not been run");
- *result = 1;
- }
- else if (res != 1)
- {
- puts ("constructor has been run without sufficient alignment");
- *result = 1;
- }
-
- resp = result;
-}
-
-static void __attribute__((destructor))
-des (void)
-{
- if (TEST_STACK_ALIGN ())
- *resp = 1;
-}
diff --git a/elf/tst-alignmod2.c b/elf/tst-alignmod2.c
deleted file mode 100644
index f338ab5c27..0000000000
--- a/elf/tst-alignmod2.c
+++ /dev/null
@@ -1,59 +0,0 @@
-/* Copyright (C) 2003-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdbool.h>
-#include <stdio.h>
-#include <tst-stack-align.h>
-#include <unistd.h>
-
-static int res, *fdp;
-static bool *test_destructorsp;
-
-static void __attribute__((constructor))
-con (void)
-{
- res = TEST_STACK_ALIGN () ? -1 : 1;
-}
-
-void
-in_dso (int *result, bool *test_destructors, int *fd)
-{
- if (!res)
- {
- puts ("constructor has not been run");
- *result = 1;
- }
- else if (res != 1)
- {
- puts ("constructor has been run without sufficient alignment");
- *result = 1;
- }
-
- test_destructorsp = test_destructors;
- fdp = fd;
-}
-
-static void __attribute__((destructor))
-des (void)
-{
- if (!test_destructorsp || !*test_destructorsp)
- return;
-
- char c = TEST_STACK_ALIGN () ? 'D' : 'C';
- write (*fdp, &c, 1);
-}
diff --git a/elf/tst-array1-static.c b/elf/tst-array1-static.c
deleted file mode 100644
index 21539a4212..0000000000
--- a/elf/tst-array1-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-array1.c"
diff --git a/elf/tst-array1.c b/elf/tst-array1.c
deleted file mode 100644
index e998932b36..0000000000
--- a/elf/tst-array1.c
+++ /dev/null
@@ -1,103 +0,0 @@
-#include <unistd.h>
-
-/* Give init non-default priority so that it runs before init_array. */
-static void init (void) __attribute__ ((constructor (1000)));
-
-static void
-init (void)
-{
- write (STDOUT_FILENO, "init\n", 5);
-}
-
-/* Give fini the same priority as init. */
-static void fini (void) __attribute__ ((destructor (1000)));
-
-static void
-fini (void)
-{
- write (STDOUT_FILENO, "fini\n", 5);
-}
-
-static void
-preinit_0 (void)
-{
- write (STDOUT_FILENO, "preinit array 0\n", 16);
-}
-
-static void
-preinit_1 (void)
-{
- write (STDOUT_FILENO, "preinit array 1\n", 16);
-}
-
-static void
-preinit_2 (void)
-{
- write (STDOUT_FILENO, "preinit array 2\n", 16);
-}
-
-void (*const preinit_array []) (void)
- __attribute__ ((section (".preinit_array"), aligned (sizeof (void *)))) =
-{
- &preinit_0,
- &preinit_1,
- &preinit_2
-};
-
-static void
-init_0 (void)
-{
- write (STDOUT_FILENO, "init array 0\n", 13);
-}
-
-static void
-init_1 (void)
-{
- write (STDOUT_FILENO, "init array 1\n", 13);
-}
-
-static void
-init_2 (void)
-{
- write (STDOUT_FILENO, "init array 2\n", 13);
-}
-
-void (*init_array []) (void)
- __attribute__ ((section (".init_array"), aligned (sizeof (void *)))) =
-{
- &init_0,
- &init_1,
- &init_2
-};
-
-static void
-fini_0 (void)
-{
- write (STDOUT_FILENO, "fini array 0\n", 13);
-}
-
-static void
-fini_1 (void)
-{
- write (STDOUT_FILENO, "fini array 1\n", 13);
-}
-
-static void
-fini_2 (void)
-{
- write (STDOUT_FILENO, "fini array 2\n", 13);
-}
-
-void (*fini_array []) (void)
- __attribute__ ((section (".fini_array"), aligned (sizeof (void *)))) =
-{
- &fini_0,
- &fini_1,
- &fini_2
-};
-
-int
-main (void)
-{
- return 0;
-}
diff --git a/elf/tst-array1.exp b/elf/tst-array1.exp
deleted file mode 100644
index cfcec9de0f..0000000000
--- a/elf/tst-array1.exp
+++ /dev/null
@@ -1,11 +0,0 @@
-preinit array 0
-preinit array 1
-preinit array 2
-init
-init array 0
-init array 1
-init array 2
-fini array 2
-fini array 1
-fini array 0
-fini
diff --git a/elf/tst-array2.c b/elf/tst-array2.c
deleted file mode 100644
index 21539a4212..0000000000
--- a/elf/tst-array2.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-array1.c"
diff --git a/elf/tst-array2.exp b/elf/tst-array2.exp
deleted file mode 100644
index ed203525b5..0000000000
--- a/elf/tst-array2.exp
+++ /dev/null
@@ -1,19 +0,0 @@
-preinit array 0
-preinit array 1
-preinit array 2
-DSO init
-DSO init array 0
-DSO init array 1
-DSO init array 2
-init
-init array 0
-init array 1
-init array 2
-fini array 2
-fini array 1
-fini array 0
-fini
-DSO fini array 2
-DSO fini array 1
-DSO fini array 0
-DSO fini
diff --git a/elf/tst-array2dep.c b/elf/tst-array2dep.c
deleted file mode 100644
index 2f920cdc8d..0000000000
--- a/elf/tst-array2dep.c
+++ /dev/null
@@ -1,71 +0,0 @@
-#include <unistd.h>
-
-/* Give init non-default priority so that it runs before init_array. */
-static void init (void) __attribute__ ((constructor (1000)));
-
-static void
-init (void)
-{
- write (STDOUT_FILENO, "DSO init\n", 9);
-}
-
-/* Give fini the same priority as init. */
-static void fini (void) __attribute__ ((destructor (1000)));
-
-static void
-fini (void)
-{
- write (STDOUT_FILENO, "DSO fini\n", 9);
-}
-
-static void
-init_0 (void)
-{
- write (STDOUT_FILENO, "DSO init array 0\n", 17);
-}
-
-static void
-init_1 (void)
-{
- write (STDOUT_FILENO, "DSO init array 1\n", 17);
-}
-
-static void
-init_2 (void)
-{
- write (STDOUT_FILENO, "DSO init array 2\n", 17);
-}
-
-void (*init_array []) (void)
- __attribute__ ((section (".init_array"), aligned (sizeof (void *)))) =
-{
- &init_0,
- &init_1,
- &init_2
-};
-
-static void
-fini_0 (void)
-{
- write (STDOUT_FILENO, "DSO fini array 0\n", 17);
-}
-
-static void
-fini_1 (void)
-{
- write (STDOUT_FILENO, "DSO fini array 1\n", 17);
-}
-
-static void
-fini_2 (void)
-{
- write (STDOUT_FILENO, "DSO fini array 2\n", 17);
-}
-
-void (*fini_array []) (void)
- __attribute__ ((section (".fini_array"), aligned (sizeof (void *)))) =
-{
- &fini_0,
- &fini_1,
- &fini_2
-};
diff --git a/elf/tst-array3.c b/elf/tst-array3.c
deleted file mode 100644
index 21539a4212..0000000000
--- a/elf/tst-array3.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-array1.c"
diff --git a/elf/tst-array4.c b/elf/tst-array4.c
deleted file mode 100644
index ac3d4eb716..0000000000
--- a/elf/tst-array4.c
+++ /dev/null
@@ -1,18 +0,0 @@
-#include <dlfcn.h>
-
-#define main array1_main
-#include "tst-array1.c"
-#undef main
-
-int
-main (void)
-{
- void *handle = dlopen ("tst-array2dep.so", RTLD_LAZY);
-
- array1_main ();
-
- if (handle != NULL)
- dlclose (handle);
-
- return 0;
-}
diff --git a/elf/tst-array4.exp b/elf/tst-array4.exp
deleted file mode 100644
index 560444d2e8..0000000000
--- a/elf/tst-array4.exp
+++ /dev/null
@@ -1,19 +0,0 @@
-preinit array 0
-preinit array 1
-preinit array 2
-init
-init array 0
-init array 1
-init array 2
-DSO init
-DSO init array 0
-DSO init array 1
-DSO init array 2
-DSO fini array 2
-DSO fini array 1
-DSO fini array 0
-DSO fini
-fini array 2
-fini array 1
-fini array 0
-fini
diff --git a/elf/tst-array5-static.c b/elf/tst-array5-static.c
deleted file mode 100644
index 4ef2aba3f3..0000000000
--- a/elf/tst-array5-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-array5.c"
diff --git a/elf/tst-array5-static.exp b/elf/tst-array5-static.exp
deleted file mode 100644
index b1dc9e467b..0000000000
--- a/elf/tst-array5-static.exp
+++ /dev/null
@@ -1,2 +0,0 @@
-preinit array in executable: tst-array5-static
-init array in executable: tst-array5-static
diff --git a/elf/tst-array5.c b/elf/tst-array5.c
deleted file mode 100644
index 03a5668326..0000000000
--- a/elf/tst-array5.c
+++ /dev/null
@@ -1,50 +0,0 @@
-#include <string.h>
-#include <unistd.h>
-
-static void
-preinit_0 (int argc __attribute__ ((unused)), char **argv)
-{
- char *p = strrchr (argv [0], '/');
-
- if (p == NULL)
- return;
-
- p++;
- size_t len = strlen (p);
- write (STDOUT_FILENO, "preinit array in executable: ", 29);
- write (STDOUT_FILENO, p, len);
- write (STDOUT_FILENO, "\n", 1);
-}
-
-void (*const preinit_array []) (int, char **)
- __attribute__ ((section (".preinit_array"), aligned (sizeof (void *)))) =
-{
- &preinit_0,
-};
-
-static void
-init_0 (int argc __attribute__ ((unused)), char **argv)
-{
- char *p = strrchr (argv [0], '/');
-
- if (p == NULL)
- return;
-
- p++;
- size_t len = strlen (p);
- write (STDOUT_FILENO, "init array in executable: ", 26);
- write (STDOUT_FILENO, p, len);
- write (STDOUT_FILENO, "\n", 1);
-}
-
-void (*const init_array []) (int, char **)
- __attribute__ ((section (".init_array"), aligned (sizeof (void *)))) =
-{
- &init_0,
-};
-
-int
-main (void)
-{
- return 0;
-}
diff --git a/elf/tst-array5.exp b/elf/tst-array5.exp
deleted file mode 100644
index 28b4909833..0000000000
--- a/elf/tst-array5.exp
+++ /dev/null
@@ -1,3 +0,0 @@
-preinit array in executable: tst-array5
-init array in DSO: tst-array5
-init array in executable: tst-array5
diff --git a/elf/tst-array5dep.c b/elf/tst-array5dep.c
deleted file mode 100644
index 570d282af4..0000000000
--- a/elf/tst-array5dep.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <string.h>
-#include <unistd.h>
-
-static void
-init_0 (int argc __attribute__ ((unused)), char **argv)
-{
- char *p = strrchr (argv [0], '/');
-
- if (p == NULL)
- return;
-
- p++;
- size_t len = strlen (p);
- write (STDOUT_FILENO, "init array in DSO: ", 19);
- write (STDOUT_FILENO, p, len);
- write (STDOUT_FILENO, "\n", 1);
-}
-
-void (*const init_array []) (int, char **)
- __attribute__ ((section (".init_array"), aligned (sizeof (void *)))) =
-{
- &init_0,
-};
diff --git a/elf/tst-audit1.c b/elf/tst-audit1.c
deleted file mode 100644
index 63656b4ee9..0000000000
--- a/elf/tst-audit1.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "../io/pwd.c"
diff --git a/elf/tst-audit11.c b/elf/tst-audit11.c
deleted file mode 100644
index ff91a6bd6d..0000000000
--- a/elf/tst-audit11.c
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Test version symbol binding can find a DSO replaced by la_objsearch.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-do_test (void)
-{
- puts ("Start");
- if (dlopen ("$ORIGIN/tst-audit11mod1.so", RTLD_LAZY) == NULL)
- {
- printf ("module not loaded: %s\n", dlerror ());
- return 1;
- }
- puts ("OK");
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-audit11mod1.c b/elf/tst-audit11mod1.c
deleted file mode 100644
index 0c0f5c6838..0000000000
--- a/elf/tst-audit11mod1.c
+++ /dev/null
@@ -1,24 +0,0 @@
-/* DSO directly opened by tst-audit11.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-extern int f2 (void);
-int
-f1 (void)
-{
- return f2 ();
-}
diff --git a/elf/tst-audit11mod2.c b/elf/tst-audit11mod2.c
deleted file mode 100644
index d5eb029744..0000000000
--- a/elf/tst-audit11mod2.c
+++ /dev/null
@@ -1,23 +0,0 @@
-/* DSO indirectly opened by tst-audit11, with symbol versioning.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-int
-f2 (void)
-{
- return 42;
-}
diff --git a/elf/tst-audit11mod2.map b/elf/tst-audit11mod2.map
deleted file mode 100644
index 278787872c..0000000000
--- a/elf/tst-audit11mod2.map
+++ /dev/null
@@ -1,22 +0,0 @@
-/* Symbol versioning for the DSO indirectly opened by tst-audit11.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-V1 {
- global: f2;
- local: *;
-};
diff --git a/elf/tst-audit12.c b/elf/tst-audit12.c
deleted file mode 100644
index 62ac5f28a4..0000000000
--- a/elf/tst-audit12.c
+++ /dev/null
@@ -1,48 +0,0 @@
-/* Test that symbol is bound to a DSO replaced by la_objsearch.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-do_test (void)
-{
- puts ("Start");
- void *h = dlopen ("$ORIGIN/tst-audit12mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("module not loaded: %s\n", dlerror ());
- return 1;
- }
- int (*fp) (void) = (int (*) (void)) dlsym (h, "f1");
- if (fp == NULL)
- {
- printf ("function f1 not found: %s\n", dlerror ());
- return 1;
- }
- int res = fp ();
- if (res != 43)
- {
- puts ("incorrect function f2 called");
- return 1;
- }
- printf ("%d is OK\n", res);
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-audit12mod1.c b/elf/tst-audit12mod1.c
deleted file mode 100644
index a48795b661..0000000000
--- a/elf/tst-audit12mod1.c
+++ /dev/null
@@ -1,24 +0,0 @@
-/* DSO directly opened by tst-audit12.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-extern int f2 (void);
-int
-f1 (void)
-{
- return f2 ();
-}
diff --git a/elf/tst-audit12mod2.c b/elf/tst-audit12mod2.c
deleted file mode 100644
index 593d02dfb6..0000000000
--- a/elf/tst-audit12mod2.c
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Replaced DSO referenced by tst-audit12mod1.so, for tst-audit12.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-int
-f2 (void)
-{
- return 42;
-}
diff --git a/elf/tst-audit12mod2.map b/elf/tst-audit12mod2.map
deleted file mode 100644
index 11e22bbdee..0000000000
--- a/elf/tst-audit12mod2.map
+++ /dev/null
@@ -1,22 +0,0 @@
-/* Symbol versioning for tst-audit12mod2.so used by tst-audit12.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-V1 {
- global: f2;
- local: *;
-};
diff --git a/elf/tst-audit12mod3.c b/elf/tst-audit12mod3.c
deleted file mode 100644
index 1e01bb8eea..0000000000
--- a/elf/tst-audit12mod3.c
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Replacement DSO loaded by the audit module, for tst-audit12.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-int
-f2 (void)
-{
- return 43;
-}
diff --git a/elf/tst-audit2.c b/elf/tst-audit2.c
deleted file mode 100644
index 0e66f5c328..0000000000
--- a/elf/tst-audit2.c
+++ /dev/null
@@ -1,60 +0,0 @@
-/* Test case for early TLS initialization in dynamic linker. */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <dlfcn.h>
-
-#define MAGIC1 0xabcdef72
-#define MAGIC2 0xd8675309
-static __thread unsigned int magic[] = { MAGIC1, MAGIC2 };
-static __thread int calloc_called;
-
-#undef calloc
-
-/* This calloc definition will be called by the dynamic linker itself.
- We test that interposed calloc is called by the dynamic loader, and
- that TLS is fully initialized by then. */
-
-void *
-calloc (size_t n, size_t m)
-{
- if (!calloc_called)
- {
- /* Allow our calloc to be called more than once. */
- calloc_called = 1;
- if (magic[0] != MAGIC1 || magic[1] != MAGIC2)
- {
- printf ("{%x, %x} != {%x, %x}\n",
- magic[0], magic[1], MAGIC1, MAGIC2);
- abort ();
- }
- magic[0] = MAGIC2;
- magic[1] = MAGIC1;
- }
-
- n *= m;
- void *ptr = malloc (n);
- if (ptr != NULL)
- memset (ptr, '\0', n);
- return ptr;
-}
-
-static int
-do_test (void)
-{
- /* Make sure that our calloc is called from the dynamic linker at least
- once. */
- void *h = dlopen("$ORIGIN/tst-auditmod9b.so", RTLD_LAZY);
- if (h != NULL)
- dlclose (h);
- if (magic[1] != MAGIC1 || magic[0] != MAGIC2)
- {
- printf ("{%x, %x} != {%x, %x}\n", magic[0], magic[1], MAGIC2, MAGIC1);
- return 1;
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-audit8.c b/elf/tst-audit8.c
deleted file mode 100644
index 63656b4ee9..0000000000
--- a/elf/tst-audit8.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "../io/pwd.c"
diff --git a/elf/tst-audit9.c b/elf/tst-audit9.c
deleted file mode 100644
index b9de1bf5a2..0000000000
--- a/elf/tst-audit9.c
+++ /dev/null
@@ -1,11 +0,0 @@
-#include <dlfcn.h>
-
-static int
-do_test (void)
-{
- void *h = dlopen("$ORIGIN/tst-auditmod9b.so", RTLD_LAZY);
- int (*fp)(void) = dlsym(h, "f");
- return fp() - 1;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-auditmod1.c b/elf/tst-auditmod1.c
deleted file mode 100644
index 573e37abd6..0000000000
--- a/elf/tst-auditmod1.c
+++ /dev/null
@@ -1,135 +0,0 @@
-#include <dlfcn.h>
-#include <link.h>
-#include <stddef.h>
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <bits/wordsize.h>
-#include <gnu/lib-names.h>
-
-
-unsigned int
-la_version (unsigned int v)
-{
- setlinebuf (stdout);
-
- printf ("version: %u\n", v);
-
- char buf[20];
- sprintf (buf, "%u", v);
-
- return v;
-}
-
-void
-la_activity (uintptr_t *cookie, unsigned int flag)
-{
- if (flag == LA_ACT_CONSISTENT)
- printf ("activity: consistent\n");
- else if (flag == LA_ACT_ADD)
- printf ("activity: add\n");
- else if (flag == LA_ACT_DELETE)
- printf ("activity: delete\n");
- else
- printf ("activity: unknown activity %u\n", flag);
-}
-
-char *
-la_objsearch (const char *name, uintptr_t *cookie, unsigned int flag)
-{
- char buf[100];
- const char *flagstr;
- if (flag == LA_SER_ORIG)
- flagstr = "LA_SET_ORIG";
- else if (flag == LA_SER_LIBPATH)
- flagstr = "LA_SER_LIBPATH";
- else if (flag == LA_SER_RUNPATH)
- flagstr = "LA_SER_RUNPATH";
- else if (flag == LA_SER_CONFIG)
- flagstr = "LA_SER_CONFIG";
- else if (flag == LA_SER_DEFAULT)
- flagstr = "LA_SER_DEFAULT";
- else if (flag == LA_SER_SECURE)
- flagstr = "LA_SER_SECURE";
- else
- {
- sprintf (buf, "unknown flag %d", flag);
- flagstr = buf;
- }
- printf ("objsearch: %s, %s\n", name, flagstr);
-
- return (char *) name;
-}
-
-unsigned int
-la_objopen (struct link_map *l, Lmid_t lmid, uintptr_t *cookie)
-{
- printf ("objopen: %ld, %s\n", lmid, l->l_name);
-
- return 3;
-}
-
-void
-la_preinit (uintptr_t *cookie)
-{
- printf ("preinit\n");
-}
-
-unsigned int
-la_objclose (uintptr_t *cookie)
-{
- printf ("objclose\n");
- return 0;
-}
-
-uintptr_t
-la_symbind32 (Elf32_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, unsigned int *flags, const char *symname)
-{
- printf ("symbind32: symname=%s, st_value=%#lx, ndx=%u, flags=%u\n",
- symname, (long int) sym->st_value, ndx, *flags);
-
- return sym->st_value;
-}
-
-uintptr_t
-la_symbind64 (Elf64_Sym *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, unsigned int *flags, const char *symname)
-{
- printf ("symbind64: symname=%s, st_value=%#lx, ndx=%u, flags=%u\n",
- symname, (long int) sym->st_value, ndx, *flags);
-
- return sym->st_value;
-}
-
-#include <tst-audit.h>
-#if (!defined (pltenter) || !defined (pltexit) || !defined (La_regs) \
- || !defined (La_retval) || !defined (int_retval))
-# error "architecture specific code needed in sysdeps/CPU/tst-audit.h"
-#endif
-
-
-ElfW(Addr)
-pltenter (ElfW(Sym) *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, La_regs *regs, unsigned int *flags,
- const char *symname, long int *framesizep)
-{
- printf ("pltenter: symname=%s, st_value=%#lx, ndx=%u, flags=%u\n",
- symname, (long int) sym->st_value, ndx, *flags);
-
- return sym->st_value;
-}
-
-unsigned int
-pltexit (ElfW(Sym) *sym, unsigned int ndx, uintptr_t *refcook,
- uintptr_t *defcook, const La_regs *inregs, La_retval *outregs,
- const char *symname)
-{
- printf ("pltexit: symname=%s, st_value=%#lx, ndx=%u, retval=%tu\n",
- symname, (long int) sym->st_value, ndx,
- (ptrdiff_t) outregs->int_retval);
-
- return 0;
-}
diff --git a/elf/tst-auditmod11.c b/elf/tst-auditmod11.c
deleted file mode 100644
index 18feb5efc4..0000000000
--- a/elf/tst-auditmod11.c
+++ /dev/null
@@ -1,39 +0,0 @@
-/* Audit module for tst-audit11.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-
-unsigned int
-la_version (unsigned int version)
-{
- return version;
-}
-
-char *
-la_objsearch (const char *name, uintptr_t *cookie, unsigned int flag)
-{
- if (strcmp (name, "tst-audit11mod2.so") == 0)
- {
- return (char *) "$ORIGIN/tst-audit11mod2.so";
- }
- return (char *) name;
-}
diff --git a/elf/tst-auditmod12.c b/elf/tst-auditmod12.c
deleted file mode 100644
index 039b7cd62b..0000000000
--- a/elf/tst-auditmod12.c
+++ /dev/null
@@ -1,43 +0,0 @@
-/* Audit module for tst-audit12.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-
-unsigned int
-la_version (unsigned int version)
-{
- return version;
-}
-
-char *
-la_objsearch (const char *name, uintptr_t *cookie, unsigned int flag)
-{
- const char target[] = "tst-audit12mod2.so";
-
- size_t namelen = strlen (name);
- if (namelen >= sizeof (target) - 1
- && strcmp (name + namelen - (sizeof (target) - 1), target) == 0)
- {
- return (char *) "$ORIGIN/tst-audit12mod3.so";
- }
- return (char *) name;
-}
diff --git a/elf/tst-auditmod9a.c b/elf/tst-auditmod9a.c
deleted file mode 100644
index 7213ade123..0000000000
--- a/elf/tst-auditmod9a.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <stdint.h>
-
-__thread int var;
-
-unsigned int
-la_version (unsigned int v)
-{
- return v;
-}
-
-void
-la_activity (uintptr_t *cookie, unsigned int flag)
-{
- ++var;
-}
diff --git a/elf/tst-auditmod9b.c b/elf/tst-auditmod9b.c
deleted file mode 100644
index 8eeeb49986..0000000000
--- a/elf/tst-auditmod9b.c
+++ /dev/null
@@ -1,6 +0,0 @@
-__thread int a;
-
-int f(void)
-{
- return ++a;
-}
diff --git a/elf/tst-auxv.c b/elf/tst-auxv.c
deleted file mode 100644
index bc571c5fa7..0000000000
--- a/elf/tst-auxv.c
+++ /dev/null
@@ -1,70 +0,0 @@
-/* Copyright (C) 2013-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <elf.h>
-#include <errno.h>
-#include <link.h>
-#include <string.h>
-#include <stdio.h>
-#include <unistd.h>
-#include <misc/sys/auxv.h>
-
-static int
-do_test (int argc, char *argv[])
-{
- errno = 0;
- const char *execfn = (const char *) getauxval (AT_NULL);
-
- if (errno != ENOENT)
- {
- printf ("errno is %d rather than %d (ENOENT) on failure\n", errno,
- ENOENT);
- return 1;
- }
-
- if (execfn != NULL)
- {
- printf ("getauxval return value is nonzero on failure\n");
- return 1;
- }
-
- errno = 0;
- execfn = (const char *) getauxval (AT_EXECFN);
-
- if (execfn == NULL)
- {
- printf ("No AT_EXECFN found, AT_EXECFN test skipped\n");
- return 0;
- }
-
- if (errno != 0)
- {
- printf ("errno erroneously set to %d on success\n", errno);
- return 1;
- }
-
- if (strcmp (argv[0], execfn) != 0)
- {
- printf ("Mismatch: argv[0]: %s vs. AT_EXECFN: %s\n", argv[0], execfn);
- return 1;
- }
-
- return 0;
-}
-
-#define TEST_FUNCTION_ARGV do_test
-#include <support/test-driver.c>
diff --git a/elf/tst-deep1.c b/elf/tst-deep1.c
deleted file mode 100644
index 97dce7ea4d..0000000000
--- a/elf/tst-deep1.c
+++ /dev/null
@@ -1,35 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-xyzzy (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return 21;
-}
-
-int
-back (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return 1;
-}
-
-extern int foo (void);
-
-static int
-do_test (void)
-{
- void *p = dlopen ("$ORIGIN/tst-deep1mod2.so", RTLD_LAZY|RTLD_DEEPBIND);
-
- int (*f) (void) = dlsym (p, "bar");
- if (f == NULL)
- {
- puts (dlerror ());
- return 1;
- }
-
- return foo () + f ();
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-deep1mod1.c b/elf/tst-deep1mod1.c
deleted file mode 100644
index cc922e6ea5..0000000000
--- a/elf/tst-deep1mod1.c
+++ /dev/null
@@ -1,14 +0,0 @@
-#include <stdio.h>
-int
-foo (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return 1;
-}
-
-int
-baz (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return 20;
-}
diff --git a/elf/tst-deep1mod2.c b/elf/tst-deep1mod2.c
deleted file mode 100644
index b99caf0328..0000000000
--- a/elf/tst-deep1mod2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-extern int baz (void);
-extern int xyzzy (void);
-int
-bar (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return baz () + xyzzy ();;
-}
-
-int
-back (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return -1;
-}
diff --git a/elf/tst-deep1mod3.c b/elf/tst-deep1mod3.c
deleted file mode 100644
index eee7d5c97b..0000000000
--- a/elf/tst-deep1mod3.c
+++ /dev/null
@@ -1,17 +0,0 @@
-#include <stdio.h>
-
-extern int back (void);
-
-int
-baz (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return back ();
-}
-
-int
-xyzzy (void)
-{
- printf ("%s:%s\n", __FILE__, __func__);
- return 0;
-}
diff --git a/elf/tst-dl-iter-static.c b/elf/tst-dl-iter-static.c
deleted file mode 100644
index 9a2758c8ef..0000000000
--- a/elf/tst-dl-iter-static.c
+++ /dev/null
@@ -1,46 +0,0 @@
-/* BZ #16046 dl_iterate_phdr static executable test.
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <link.h>
-
-/* Check that the link map of the static executable itself is iterated
- over exactly once. */
-
-static int
-callback (struct dl_phdr_info *info, size_t size, void *data)
-{
- int *count = data;
-
- if (info->dlpi_name[0] == '\0')
- (*count)++;
-
- return 0;
-}
-
-static int
-do_test (void)
-{
- int count = 0;
- int status;
-
- status = dl_iterate_phdr (callback, &count);
-
- return status || count != 1;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlmodcount.c b/elf/tst-dlmodcount.c
deleted file mode 100644
index 34c5b25d7f..0000000000
--- a/elf/tst-dlmodcount.c
+++ /dev/null
@@ -1,108 +0,0 @@
-/* Copyright (C) 2004-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by David Mosberger <davidm@hpl.hp.com>, 2004.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <link.h>
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#define SET 0
-#define ADD 1
-#define REMOVE 2
-
-#define leq(l,r) (((r) - (l)) <= ~0ULL / 2)
-
-static int
-callback (struct dl_phdr_info *info, size_t size, void *ptr)
-{
- static int last_adds = 0, last_subs = 0;
- intptr_t cmd = (intptr_t) ptr;
-
- printf (" size = %Zu\n", size);
- if (size < (offsetof (struct dl_phdr_info, dlpi_subs)
- + sizeof (info->dlpi_subs)))
- {
- fprintf (stderr, "dl_iterate_phdr failed to pass dlpi_adds/dlpi_subs\n");
- exit (5);
- }
-
- printf (" dlpi_adds = %Lu dlpi_subs = %Lu\n",
- info->dlpi_adds, info->dlpi_subs);
-
- switch (cmd)
- {
- case SET:
- break;
-
- case ADD:
- if (leq (info->dlpi_adds, last_adds))
- {
- fprintf (stderr, "dlpi_adds failed to get incremented!\n");
- exit (3);
- }
- break;
-
- case REMOVE:
- if (leq (info->dlpi_subs, last_subs))
- {
- fprintf (stderr, "dlpi_subs failed to get incremented!\n");
- exit (4);
- }
- break;
- }
- last_adds = info->dlpi_adds;
- last_subs = info->dlpi_subs;
- return -1;
-}
-
-static void *
-load (const char *path)
-{
- void *handle;
-
- printf ("loading `%s'\n", path);
- handle = dlopen (path, RTLD_LAZY);
- if (!handle)
- exit (1);
- dl_iterate_phdr (callback, (void *)(intptr_t) ADD);
- return handle;
-}
-
-static void
-unload (const char *path, void *handle)
-{
- printf ("unloading `%s'\n", path);
- if (dlclose (handle) < 0)
- exit (2);
- dl_iterate_phdr (callback, (void *)(intptr_t) REMOVE);
-}
-
-static int
-do_test (void)
-{
- void *handle1, *handle2;
-
- dl_iterate_phdr (callback, (void *)(intptr_t) SET);
- handle1 = load ("firstobj.so");
- handle2 = load ("globalmod1.so");
- unload ("firstobj.so", handle1);
- unload ("globalmod1.so", handle2);
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlmopen1.c b/elf/tst-dlmopen1.c
deleted file mode 100644
index 24145cfca6..0000000000
--- a/elf/tst-dlmopen1.c
+++ /dev/null
@@ -1,80 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <gnu/lib-names.h>
-
-#define TEST_SO "$ORIGIN/tst-dlmopen1mod.so"
-
-static int
-do_test (void)
-{
- void *h = dlopen (LIBC_SO, RTLD_LAZY|RTLD_NOLOAD);
- if (h == NULL)
- {
- printf ("cannot get handle for %s: %s\n", LIBC_SO, dlerror ());
- return 1;
- }
-
- Lmid_t ns = -10;
- if (dlinfo (h, RTLD_DI_LMID, &ns) != 0)
- {
- printf ("dlinfo for %s in %s failed: %s\n",
- LIBC_SO, __func__, dlerror ());
- return 1;
- }
-
- if (ns != LM_ID_BASE)
- {
- printf ("namespace for %s not LM_ID_BASE\n", LIBC_SO);
- return 1;
- }
-
- if (dlclose (h) != 0)
- {
- printf ("dlclose for %s in %s failed: %s\n",
- LIBC_SO, __func__, dlerror ());
- return 1;
- }
-
- h = dlmopen (LM_ID_NEWLM, TEST_SO, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot get handle for %s: %s\n",
- "tst-dlmopen1mod.so", dlerror ());
- return 1;
- }
-
- ns = -10;
- if (dlinfo (h, RTLD_DI_LMID, &ns) != 0)
- {
- printf ("dlinfo for %s in %s failed: %s\n",
- "tst-dlmopen1mod.so", __func__, dlerror ());
- return 1;
- }
-
- if (ns == LM_ID_BASE)
- {
- printf ("namespace for %s is LM_ID_BASE\n", TEST_SO);
- return 1;
- }
-
- int (*fct) (Lmid_t) = dlsym (h, "foo");
- if (fct == NULL)
- {
- printf ("could not find %s: %s\n", "foo", dlerror ());
- return 1;
- }
-
- if (fct (ns) != 0)
- return 1;
-
- if (dlclose (h) != 0)
- {
- printf ("dlclose for %s in %s failed: %s\n",
- TEST_SO, __func__, dlerror ());
- return 1;
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlmopen1mod.c b/elf/tst-dlmopen1mod.c
deleted file mode 100644
index 142488098a..0000000000
--- a/elf/tst-dlmopen1mod.c
+++ /dev/null
@@ -1,59 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <gnu/lib-names.h>
-
-
-static int cnt;
-
-static void
-__attribute ((constructor))
-constr (void)
-{
- ++cnt;
-}
-
-
-int
-foo (Lmid_t ns2)
-{
- void *h = dlopen (LIBC_SO, RTLD_LAZY|RTLD_NOLOAD);
- if (h == NULL)
- {
- printf ("cannot get handle for %s: %s\n", LIBC_SO, dlerror ());
- return 1;
- }
-
- Lmid_t ns = -10;
- if (dlinfo (h, RTLD_DI_LMID, &ns) != 0)
- {
- printf ("dlinfo for %s in %s failed: %s\n",
- LIBC_SO, __func__, dlerror ());
- return 1;
- }
-
- if (ns != ns2)
- {
- printf ("namespace for %s not LM_ID_BASE\n", LIBC_SO);
- return 1;
- }
-
- if (dlclose (h) != 0)
- {
- printf ("dlclose for %s in %s failed: %s\n",
- LIBC_SO, __func__, dlerror ());
- return 1;
- }
-
- if (cnt == 0)
- {
- puts ("constructor did not run");
- return 1;
- }
- else if (cnt != 1)
- {
- puts ("constructor did not run exactly once");
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/tst-dlmopen2.c b/elf/tst-dlmopen2.c
deleted file mode 100644
index 8489ffba08..0000000000
--- a/elf/tst-dlmopen2.c
+++ /dev/null
@@ -1,69 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <string.h>
-#include <gnu/lib-names.h>
-#include <ldsodefs.h>
-
-
-static int
-do_test (void)
-{
- int result = 0;
-
- for (int i = 1; i <= 10; ++i)
- {
- void *h[DL_NNS - 1];
- char used[DL_NNS];
-
- printf ("round %d\n", i);
-
- memset (used, '\0', sizeof (used));
- used[LM_ID_BASE] = 1;
-
- for (int j = 0; j < DL_NNS - 1; ++j)
- {
- h[j] = dlmopen (LM_ID_NEWLM, "$ORIGIN/tst-dlmopen1mod.so",
- RTLD_LAZY);
- if (h[j] == NULL)
- {
- printf ("round %d, namespace %d: load failed: %s\n",
- i, j, dlerror ());
- return 1;
- }
- Lmid_t ns;
- if (dlinfo (h[j], RTLD_DI_LMID, &ns) != 0)
- {
- printf ("round %d, namespace %d: dlinfo failed: %s\n",
- i, j, dlerror ());
- return 1;
- }
- if (ns < 0 || ns >= DL_NNS)
- {
- printf ("round %d, namespace %d: invalid namespace %ld",
- i, j, (long int) ns);
- result = 1;
- }
- else if (used[ns] != 0)
- {
- printf ("\
-round %d, namespace %d: duplicate allocate of namespace %ld",
- i, j, (long int) ns);
- result = 1;
- }
- else
- used[ns] = 1;
- }
-
- for (int j = 0; j < DL_NNS - 1; ++j)
- if (dlclose (h[j]) != 0)
- {
- printf ("round %d, namespace %d: close failed: %s\n",
- i, j, dlerror ());
- return 1;
- }
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlmopen3.c b/elf/tst-dlmopen3.c
deleted file mode 100644
index 8167507784..0000000000
--- a/elf/tst-dlmopen3.c
+++ /dev/null
@@ -1,21 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-
-static int
-do_test (void)
-{
- void *h = dlmopen (LM_ID_NEWLM, "$ORIGIN/tst-dlmopen1mod.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot get handle for %s: %s\n",
- "tst-dlmopen1mod.so", dlerror ());
- return 1;
- }
-
- /* Do not unload. */
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlopen-aout.c b/elf/tst-dlopen-aout.c
deleted file mode 100644
index cccc508966..0000000000
--- a/elf/tst-dlopen-aout.c
+++ /dev/null
@@ -1,67 +0,0 @@
-/* Test case for BZ #16634.
-
- Verify that incorrectly dlopen()ing an executable without
- __RTLD_OPENEXEC does not cause assertion in ld.so.
-
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>.
-
- Note: this test currently only fails when glibc is configured with
- --enable-hardcoded-path-in-tests. */
-
-#include <assert.h>
-#include <dlfcn.h>
-#include <stdio.h>
-#include <pthread.h>
-
-__thread int x;
-
-void *
-fn (void *p)
-{
- return p;
-}
-
-static int
-do_test (int argc, char *argv[])
-{
- int j;
-
- for (j = 0; j < 100; ++j)
- {
- pthread_t thr;
- void *p;
- int rc;
-
- p = dlopen (argv[0], RTLD_LAZY);
- if (p != NULL)
- {
- fprintf (stderr, "dlopen unexpectedly succeeded\n");
- return 1;
- }
- rc = pthread_create (&thr, NULL, fn, NULL);
- assert (rc == 0);
-
- rc = pthread_join (thr, NULL);
- assert (rc == 0);
- }
-
- return 0;
-}
-
-#define TEST_FUNCTION_ARGV do_test
-#include <support/test-driver.c>
diff --git a/elf/tst-dlopenrpath.c b/elf/tst-dlopenrpath.c
deleted file mode 100644
index 77346d36f9..0000000000
--- a/elf/tst-dlopenrpath.c
+++ /dev/null
@@ -1,70 +0,0 @@
-/* Copyright (C) 2004-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@redhat.com>, 2004.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <errno.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <sys/stat.h>
-
-
-extern int foo (void);
-
-static const char testsubdir[] = PFX "test-subdir";
-
-
-static int
-do_test (void)
-{
- struct stat64 st;
- int result = 1;
-
- if (mkdir (testsubdir, 0777) != 0
- && (errno != EEXIST
- || stat64 (testsubdir, &st) != 0
- || !S_ISDIR (st.st_mode)))
- {
- printf ("cannot create directory %s\n", testsubdir);
- return 1;
- }
-
- if (system ("cp " PFX "firstobj.so " PFX "test-subdir/in-subdir.so") != 0)
- {
- puts ("cannot copy DSO");
- return 1;
- }
-
- void *p = dlopen ("in-subdir.so", RTLD_LAZY|RTLD_LOCAL);
- if (p != NULL)
- {
- puts ("succeeded in opening in-subdir.so from do_test");
- dlclose (p);
- goto out;
- }
-
- result = foo ();
-
- out:
- unlink (PFX "test-subdir/in-subdir.so");
- rmdir (testsubdir);
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-dlopenrpathmod.c b/elf/tst-dlopenrpathmod.c
deleted file mode 100644
index 6d244401bf..0000000000
--- a/elf/tst-dlopenrpathmod.c
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Copyright (C) 2004-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Ulrich Drepper <drepper@redhat.com>, 2004.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-
-
-int
-foo (void)
-{
- void *p = dlopen ("in-subdir.so", RTLD_LAZY|RTLD_LOCAL);
- if (p != NULL)
- {
- dlclose (p);
- return 0;
- }
-
- puts ("couldn't open in-subdir.so from foo");
- return 1;
-}
diff --git a/elf/tst-dlsym-error.c b/elf/tst-dlsym-error.c
deleted file mode 100644
index fac8f10ccf..0000000000
--- a/elf/tst-dlsym-error.c
+++ /dev/null
@@ -1,113 +0,0 @@
-/* Test error reporting for dlsym, dlvsym failures.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <gnu/lib-names.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-/* Used to disambiguate symbol names. */
-static int counter;
-
-static void
-test_one (void *handle, const char *name, void *(func) (void *, const char *),
- const char *suffix)
-{
- ++counter;
- char symbol[32];
- snprintf (symbol, sizeof (symbol), "no_such_symbol_%d", counter);
- char *expected_message;
- if (asprintf (&expected_message, ": undefined symbol: %s%s",
- symbol, suffix) < 0)
- {
- printf ("error: asprintf: %m\n");
- abort ();
- }
-
- void *addr = func (handle, symbol);
- if (addr != NULL)
- {
- printf ("error: %s: found symbol \"no_such_symbol\"\n", name);
- abort ();
- }
- const char *message = dlerror ();
- if (message == NULL)
- {
- printf ("error: %s: missing error message\n", name);
- abort ();
- }
- const char *message_without_path = strchrnul (message, ':');
- if (strcmp (message_without_path, expected_message) != 0)
- {
- printf ("error: %s: unexpected error message: %s\n", name, message);
- abort ();
- }
- free (expected_message);
-
- message = dlerror ();
- if (message != NULL)
- {
- printf ("error: %s: unexpected error message: %s\n", name, message);
- abort ();
- }
-}
-
-static void
-test_handles (const char *name, void *(func) (void *, const char *),
- const char *suffix)
-{
- test_one (RTLD_DEFAULT, name, func, suffix);
- test_one (RTLD_NEXT, name, func, suffix);
-
- void *handle = dlopen (LIBC_SO, RTLD_LAZY);
- if (handle == NULL)
- {
- printf ("error: cannot dlopen %s: %s\n", LIBC_SO, dlerror ());
- abort ();
- }
- test_one (handle, name, func, suffix);
- dlclose (handle);
-}
-
-static void *
-dlvsym_no_such_version (void *handle, const char *name)
-{
- return dlvsym (handle, name, "NO_SUCH_VERSION");
-}
-
-static void *
-dlvsym_glibc_private (void *handle, const char *name)
-{
- return dlvsym (handle, name, "GLIBC_PRIVATE");
-}
-
-static int
-do_test (void)
-{
- test_handles ("dlsym", dlsym, "");
- test_handles ("dlvsym", dlvsym_no_such_version,
- ", version NO_SUCH_VERSION");
- test_handles ("dlvsym", dlvsym_glibc_private,
- ", version GLIBC_PRIVATE");
-
- return 0;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-env-setuid-tunables.c b/elf/tst-env-setuid-tunables.c
deleted file mode 100644
index afcb146e6d..0000000000
--- a/elf/tst-env-setuid-tunables.c
+++ /dev/null
@@ -1,75 +0,0 @@
-/* Copyright (C) 2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Verify that tunables correctly filter out unsafe tunables like
- glibc.malloc.check and glibc.malloc.mmap_threshold but also retain
- glibc.malloc.mmap_threshold in an unprivileged child. */
-
-/* This is compiled as part of the testsuite but needs to see
- HAVE_TUNABLES. */
-#define _LIBC 1
-#include "config.h"
-#undef _LIBC
-
-#define test_parent test_parent_tunables
-#define test_child test_child_tunables
-
-static int test_child_tunables (void);
-static int test_parent_tunables (void);
-
-#include "tst-env-setuid.c"
-
-#define CHILD_VALSTRING_VALUE "glibc.malloc.mmap_threshold=4096"
-#define PARENT_VALSTRING_VALUE \
- "glibc.malloc.check=2:glibc.malloc.mmap_threshold=4096"
-
-static int
-test_child_tunables (void)
-{
- const char *val = getenv ("GLIBC_TUNABLES");
-
-#if HAVE_TUNABLES
- if (val != NULL && strcmp (val, CHILD_VALSTRING_VALUE) == 0)
- return 0;
-
- if (val != NULL)
- printf ("Unexpected GLIBC_TUNABLES VALUE %s\n", val);
-
- return 1;
-#else
- if (val != NULL)
- {
- printf ("GLIBC_TUNABLES not cleared\n");
- return 1;
- }
- return 0;
-#endif
-}
-
-static int
-test_parent_tunables (void)
-{
- const char *val = getenv ("GLIBC_TUNABLES");
-
- if (val != NULL && strcmp (val, PARENT_VALSTRING_VALUE) == 0)
- return 0;
-
- if (val != NULL)
- printf ("Unexpected GLIBC_TUNABLES VALUE %s\n", val);
-
- return 1;
-}
diff --git a/elf/tst-env-setuid.c b/elf/tst-env-setuid.c
deleted file mode 100644
index eec408eb5d..0000000000
--- a/elf/tst-env-setuid.c
+++ /dev/null
@@ -1,296 +0,0 @@
-/* Copyright (C) 2012-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Verify that tunables correctly filter out unsafe environment variables like
- MALLOC_CHECK_ and MALLOC_MMAP_THRESHOLD_ but also retain
- MALLOC_MMAP_THRESHOLD_ in an unprivileged child. */
-
-#include <errno.h>
-#include <fcntl.h>
-#include <stdlib.h>
-#include <stdint.h>
-#include <stdio.h>
-#include <string.h>
-#include <sys/stat.h>
-#include <sys/wait.h>
-#include <unistd.h>
-
-#include <support/support.h>
-#include <support/test-driver.h>
-
-static char SETGID_CHILD[] = "setgid-child";
-#define CHILD_STATUS 42
-
-/* Return a GID which is not our current GID, but is present in the
- supplementary group list. */
-static gid_t
-choose_gid (void)
-{
- const int count = 64;
- gid_t groups[count];
- int ret = getgroups (count, groups);
- if (ret < 0)
- {
- printf ("getgroups: %m\n");
- exit (1);
- }
- gid_t current = getgid ();
- for (int i = 0; i < ret; ++i)
- {
- if (groups[i] != current)
- return groups[i];
- }
- return 0;
-}
-
-/* Spawn and execute a program and verify that it returns the CHILD_STATUS. */
-static pid_t
-do_execve (char **args)
-{
- pid_t kid = vfork ();
-
- if (kid < 0)
- {
- printf ("vfork: %m\n");
- return -1;
- }
-
- if (kid == 0)
- {
- /* Child process. */
- execve (args[0], args, environ);
- _exit (-errno);
- }
-
- if (kid < 0)
- return 1;
-
- int status;
-
- if (waitpid (kid, &status, 0) < 0)
- {
- printf ("waitpid: %m\n");
- return 1;
- }
-
- if (WEXITSTATUS (status) == EXIT_UNSUPPORTED)
- return EXIT_UNSUPPORTED;
-
- if (!WIFEXITED (status) || WEXITSTATUS (status) != CHILD_STATUS)
- {
- printf ("Unexpected exit status %d from child process\n",
- WEXITSTATUS (status));
- return 1;
- }
- return 0;
-}
-
-/* Copies the executable into a restricted directory, so that we can
- safely make it SGID with the TARGET group ID. Then runs the
- executable. */
-static int
-run_executable_sgid (gid_t target)
-{
- char *dirname = xasprintf ("%s/tst-tunables-setuid.%jd",
- test_dir, (intmax_t) getpid ());
- char *execname = xasprintf ("%s/bin", dirname);
- int infd = -1;
- int outfd = -1;
- int ret = 0;
- if (mkdir (dirname, 0700) < 0)
- {
- printf ("mkdir: %m\n");
- goto err;
- }
- infd = open ("/proc/self/exe", O_RDONLY);
- if (infd < 0)
- {
- printf ("open (/proc/self/exe): %m\n");
- goto err;
- }
- outfd = open (execname, O_WRONLY | O_CREAT | O_EXCL, 0700);
- if (outfd < 0)
- {
- printf ("open (%s): %m\n", execname);
- goto err;
- }
- char buf[4096];
- for (;;)
- {
- ssize_t rdcount = read (infd, buf, sizeof (buf));
- if (rdcount < 0)
- {
- printf ("read: %m\n");
- goto err;
- }
- if (rdcount == 0)
- break;
- char *p = buf;
- char *end = buf + rdcount;
- while (p != end)
- {
- ssize_t wrcount = write (outfd, buf, end - p);
- if (wrcount == 0)
- errno = ENOSPC;
- if (wrcount <= 0)
- {
- printf ("write: %m\n");
- goto err;
- }
- p += wrcount;
- }
- }
- if (fchown (outfd, getuid (), target) < 0)
- {
- printf ("fchown (%s): %m\n", execname);
- goto err;
- }
- if (fchmod (outfd, 02750) < 0)
- {
- printf ("fchmod (%s): %m\n", execname);
- goto err;
- }
- if (close (outfd) < 0)
- {
- printf ("close (outfd): %m\n");
- goto err;
- }
- if (close (infd) < 0)
- {
- printf ("close (infd): %m\n");
- goto err;
- }
-
- char *args[] = {execname, SETGID_CHILD, NULL};
-
- ret = do_execve (args);
-
-err:
- if (outfd >= 0)
- close (outfd);
- if (infd >= 0)
- close (infd);
- if (execname)
- {
- unlink (execname);
- free (execname);
- }
- if (dirname)
- {
- rmdir (dirname);
- free (dirname);
- }
- return ret;
-}
-
-#ifndef test_child
-static int
-test_child (void)
-{
- if (getenv ("MALLOC_CHECK_") != NULL)
- {
- printf ("MALLOC_CHECK_ is still set\n");
- return 1;
- }
-
- if (getenv ("MALLOC_MMAP_THRESHOLD_") == NULL)
- {
- printf ("MALLOC_MMAP_THRESHOLD_ lost\n");
- return 1;
- }
-
- if (getenv ("LD_HWCAP_MASK") != NULL)
- {
- printf ("LD_HWCAP_MASK still set\n");
- return 1;
- }
-
- return 0;
-}
-#endif
-
-#ifndef test_parent
-static int
-test_parent (void)
-{
- if (getenv ("MALLOC_CHECK_") == NULL)
- {
- printf ("MALLOC_CHECK_ lost\n");
- return 1;
- }
-
- if (getenv ("MALLOC_MMAP_THRESHOLD_") == NULL)
- {
- printf ("MALLOC_MMAP_THRESHOLD_ lost\n");
- return 1;
- }
-
- if (getenv ("LD_HWCAP_MASK") == NULL)
- {
- printf ("LD_HWCAP_MASK lost\n");
- return 1;
- }
-
- return 0;
-}
-#endif
-
-static int
-do_test (int argc, char **argv)
-{
- /* Setgid child process. */
- if (argc == 2 && strcmp (argv[1], SETGID_CHILD) == 0)
- {
- if (getgid () == getegid ())
- {
- /* This can happen if the file system is mounted nosuid. */
- fprintf (stderr, "SGID failed: GID and EGID match (%jd)\n",
- (intmax_t) getgid ());
- exit (EXIT_UNSUPPORTED);
- }
-
- int ret = test_child ();
-
- if (ret != 0)
- exit (1);
-
- exit (CHILD_STATUS);
- }
- else
- {
- if (test_parent () != 0)
- exit (1);
-
- /* Try running a setgid program. */
- gid_t target = choose_gid ();
- if (target == 0)
- {
- fprintf (stderr,
- "Could not find a suitable GID for user %jd, skipping test\n",
- (intmax_t) getuid ());
- exit (0);
- }
-
- return run_executable_sgid (target);
- }
-
- /* Something went wrong and our argv was corrupted. */
- _exit (1);
-}
-
-#define TEST_FUNCTION_ARGV do_test
-#include <support/test-driver.c>
diff --git a/elf/tst-execstack-mod.c b/elf/tst-execstack-mod.c
deleted file mode 100644
index 038e6550b5..0000000000
--- a/elf/tst-execstack-mod.c
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Test module for making nonexecutable stacks executable
- on load of a DSO that requires executable stacks. */
-
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-void callme (void (*callback) (void));
-
-/* This is a function that makes use of executable stack by
- using a local function trampoline. */
-void
-tryme (void)
-{
- bool ok = false;
- void callback (void) { ok = true; }
-
- callme (&callback);
-
- if (ok)
- printf ("DSO called ok (local %p, trampoline %p)\n", &ok, &callback);
- else
- abort ();
-}
-
-void
-callme (void (*callback) (void))
-{
- (*callback) ();
-}
diff --git a/elf/tst-execstack-needed.c b/elf/tst-execstack-needed.c
deleted file mode 100644
index 8b794a3d47..0000000000
--- a/elf/tst-execstack-needed.c
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Test program for making nonexecutable stacks executable
- on DT_NEEDED load of a DSO that requires executable stacks. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <error.h>
-
-extern void tryme (void); /* from tst-execstack-mod.so */
-
-static void deeper (void (*f) (void));
-
-static int
-do_test (void)
-{
- tryme ();
-
- /* Test that growing the stack region gets new executable pages too. */
- deeper (&tryme);
-
- return 0;
-}
-
-static void
-deeper (void (*f) (void))
-{
- char stack[1100 * 1024];
- memfrob (stack, sizeof stack);
- (*f) ();
- memfrob (stack, sizeof stack);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-execstack-prog.c b/elf/tst-execstack-prog.c
deleted file mode 100644
index 8663153372..0000000000
--- a/elf/tst-execstack-prog.c
+++ /dev/null
@@ -1,33 +0,0 @@
-/* Test program for executable stacks in an executable itself. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <error.h>
-
-#include "tst-execstack-mod.c" /* This defines the `tryme' test function. */
-
-static void deeper (void (*f) (void));
-
-static int
-do_test (void)
-{
- tryme ();
-
- /* Test that growing the stack region gets new executable pages too. */
- deeper (&tryme);
-
- return 0;
-}
-
-static void
-deeper (void (*f) (void))
-{
- char stack[1100 * 1024];
- memfrob (stack, sizeof stack);
- (*f) ();
- memfrob (stack, sizeof stack);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-execstack.c b/elf/tst-execstack.c
deleted file mode 100644
index 114f341d76..0000000000
--- a/elf/tst-execstack.c
+++ /dev/null
@@ -1,236 +0,0 @@
-/* Test program for making nonexecutable stacks executable
- on load of a DSO that requires executable stacks. */
-
-#include <dlfcn.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <error.h>
-#include <stackinfo.h>
-
-static void
-print_maps (void)
-{
-#if 0
- char *cmd = NULL;
- asprintf (&cmd, "cat /proc/%d/maps", getpid ());
- system (cmd);
- free (cmd);
-#endif
-}
-
-static void deeper (void (*f) (void));
-
-#if USE_PTHREADS
-# include <pthread.h>
-
-static void *
-tryme_thread (void *f)
-{
- (*((void (*) (void)) f)) ();
-
- return 0;
-}
-
-static pthread_barrier_t startup_barrier, go_barrier;
-static void *
-waiter_thread (void *arg)
-{
- void **f = arg;
- pthread_barrier_wait (&startup_barrier);
- pthread_barrier_wait (&go_barrier);
-
- (*((void (*) (void)) *f)) ();
-
- return 0;
-}
-#endif
-
-static bool allow_execstack = true;
-
-
-static int
-do_test (void)
-{
- /* Check whether SELinux is enabled and disallows executable stacks. */
- FILE *fp = fopen ("/selinux/enforce", "r");
- if (fp != NULL)
- {
- char *line = NULL;
- size_t linelen = 0;
-
- bool enabled = false;
- ssize_t n = getline (&line, &linelen, fp);
- if (n > 0 && line[0] != '0')
- enabled = true;
-
- fclose (fp);
-
- if (enabled)
- {
- fp = fopen ("/selinux/booleans/allow_execstack", "r");
- if (fp != NULL)
- {
- n = getline (&line, &linelen, fp);
- if (n > 0 && line[0] == '0')
- allow_execstack = false;
- }
-
- fclose (fp);
- }
- }
-
- printf ("executable stacks %sallowed\n", allow_execstack ? "" : "not ");
-
- static void *f; /* Address of this is used in other threads. */
-
-#if USE_PTHREADS
- /* Create some threads while stacks are nonexecutable. */
- #define N 5
- pthread_t thr[N];
-
- pthread_barrier_init (&startup_barrier, NULL, N + 1);
- pthread_barrier_init (&go_barrier, NULL, N + 1);
-
- for (int i = 0; i < N; ++i)
- {
- int rc = pthread_create (&thr[i], NULL, &waiter_thread, &f);
- if (rc)
- error (1, rc, "pthread_create");
- }
-
- /* Make sure they are all there using their stacks. */
- pthread_barrier_wait (&startup_barrier);
- puts ("threads waiting");
-#endif
-
- print_maps ();
-
-#if USE_PTHREADS
- void *old_stack_addr, *new_stack_addr;
- size_t stack_size;
- pthread_t me = pthread_self ();
- pthread_attr_t attr;
- int ret = 0;
-
- ret = pthread_getattr_np (me, &attr);
- if (ret)
- {
- printf ("before execstack: pthread_getattr_np returned error: %s\n",
- strerror (ret));
- return 1;
- }
-
- ret = pthread_attr_getstack (&attr, &old_stack_addr, &stack_size);
- if (ret)
- {
- printf ("before execstack: pthread_attr_getstack returned error: %s\n",
- strerror (ret));
- return 1;
- }
-# if _STACK_GROWS_DOWN
- old_stack_addr += stack_size;
-# else
- old_stack_addr -= stack_size;
-# endif
-#endif
-
- /* Loading this module should force stacks to become executable. */
- void *h = dlopen ("tst-execstack-mod.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot load: %s\n", dlerror ());
- return allow_execstack;
- }
-
- f = dlsym (h, "tryme");
- if (f == NULL)
- {
- printf ("symbol not found: %s\n", dlerror ());
- return 1;
- }
-
- /* Test if that really made our stack executable.
- The `tryme' function should crash if not. */
-
- (*((void (*) (void)) f)) ();
-
- print_maps ();
-
-#if USE_PTHREADS
- ret = pthread_getattr_np (me, &attr);
- if (ret)
- {
- printf ("after execstack: pthread_getattr_np returned error: %s\n",
- strerror (ret));
- return 1;
- }
-
- ret = pthread_attr_getstack (&attr, &new_stack_addr, &stack_size);
- if (ret)
- {
- printf ("after execstack: pthread_attr_getstack returned error: %s\n",
- strerror (ret));
- return 1;
- }
-
-# if _STACK_GROWS_DOWN
- new_stack_addr += stack_size;
-# else
- new_stack_addr -= stack_size;
-# endif
-
- /* It is possible that the dlopen'd module may have been mmapped just below
- the stack. The stack size is taken as MIN(stack rlimit size, end of last
- vma) in pthread_getattr_np. If rlimit is set high enough, it is possible
- that the size may have changed. A subsequent call to
- pthread_attr_getstack returns the size and (bottom - size) as the
- stacksize and stackaddr respectively. If the size changes due to the
- above, then both stacksize and stackaddr can change, but the stack bottom
- should remain the same, which is computed as stackaddr + stacksize. */
- if (old_stack_addr != new_stack_addr)
- {
- printf ("Stack end changed, old: %p, new: %p\n",
- old_stack_addr, new_stack_addr);
- return 1;
- }
- printf ("Stack address remains the same: %p\n", old_stack_addr);
-#endif
-
- /* Test that growing the stack region gets new executable pages too. */
- deeper ((void (*) (void)) f);
-
- print_maps ();
-
-#if USE_PTHREADS
- /* Test that a fresh thread now gets an executable stack. */
- {
- pthread_t th;
- int rc = pthread_create (&th, NULL, &tryme_thread, f);
- if (rc)
- error (1, rc, "pthread_create");
- }
-
- puts ("threads go");
- /* The existing threads' stacks should have been changed.
- Let them run to test it. */
- pthread_barrier_wait (&go_barrier);
-
- pthread_exit ((void *) (long int) (! allow_execstack));
-#endif
-
- return ! allow_execstack;
-}
-
-static void
-deeper (void (*f) (void))
-{
- char stack[1100 * 1024];
- memfrob (stack, sizeof stack);
- (*f) ();
- memfrob (stack, sizeof stack);
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-global1.c b/elf/tst-global1.c
deleted file mode 100644
index 5dae74eec0..0000000000
--- a/elf/tst-global1.c
+++ /dev/null
@@ -1,38 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- void *h1 = dlopen ("$ORIGIN/testobj6.so", RTLD_GLOBAL|RTLD_LAZY);
- if (h1 == NULL)
- {
- puts ("cannot open testobj6");
- return 1;
- }
-
- void *h2 = dlopen ("$ORIGIN/testobj2.so",
- RTLD_GLOBAL|RTLD_DEEPBIND|RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("cannot open testobj2");
- return 1;
- }
-
- dlclose (h1);
-
- void (*f) (void) = dlsym (h2, "p");
- if (f == NULL)
- {
- puts ("cannot find p");
- return 1;
- }
-
- f ();
-
- dlclose (h2);
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-gnu2-tls1.c b/elf/tst-gnu2-tls1.c
deleted file mode 100644
index b33b60a301..0000000000
--- a/elf/tst-gnu2-tls1.c
+++ /dev/null
@@ -1,51 +0,0 @@
-/* Test local and global dynamic models for GNU2 TLS.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdio.h>
-#include <stdlib.h>
-
-extern int * get_gd (void);
-extern void set_gd (int);
-extern int test_gd (int);
-extern int * get_ld (void);
-extern void set_ld (int);
-extern int test_ld (int);
-
-__thread int gd = 1;
-
-static int
-do_test (void)
-{
- int *p;
-
- p = get_gd ();
- set_gd (3);
- if (*p != 3 || !test_gd (3))
- abort ();
-
- p = get_ld ();
- set_ld (4);
- if (*p != 4 || !test_ld (4))
- abort ();
-
- printf ("PASS\n");
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-gnu2-tls1mod.c b/elf/tst-gnu2-tls1mod.c
deleted file mode 100644
index fa76ab1222..0000000000
--- a/elf/tst-gnu2-tls1mod.c
+++ /dev/null
@@ -1,56 +0,0 @@
-/* DSO used by tst-gnu2-tls1.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-static __thread int ld;
-
-int *
-get_ld (void)
-{
- return &ld;
-}
-
-void
-set_ld (int i)
-{
- ld = i;
-}
-
-int
-test_ld (int i)
-{
- return ld == i;
-}
-extern __thread int gd;
-
-int *
-get_gd (void)
-{
- return &gd;
-}
-
-void
-set_gd (int i)
-{
- gd = i;
-}
-
-int
-test_gd (int i)
-{
- return gd == i;
-}
diff --git a/elf/tst-initorder.c b/elf/tst-initorder.c
deleted file mode 100644
index 9638382104..0000000000
--- a/elf/tst-initorder.c
+++ /dev/null
@@ -1,7 +0,0 @@
-#include <stdio.h>
-
-int
-main( int argc, char *argv[] )
-{
- printf( "main\n" );
-}
diff --git a/elf/tst-initorder.exp b/elf/tst-initorder.exp
deleted file mode 100644
index 8718f65765..0000000000
--- a/elf/tst-initorder.exp
+++ /dev/null
@@ -1,13 +0,0 @@
-start_a1
-start_a2
-start_b1
-start_b2
-start_a3
-start_a4
-main
-finish_a4
-finish_a3
-finish_b2
-finish_b1
-finish_a2
-finish_a1
diff --git a/elf/tst-initorder2.c b/elf/tst-initorder2.c
deleted file mode 100644
index 050f9568b8..0000000000
--- a/elf/tst-initorder2.c
+++ /dev/null
@@ -1,20 +0,0 @@
-#include <stdio.h>
-
-#ifndef NAME
-int
-main (void)
-{
- puts ("main");
-}
-#else
-static void __attribute__ ((constructor))
-init (void)
-{
- puts ("init: " NAME);
-}
-static void __attribute__ ((destructor))
-fini (void)
-{
- puts ("fini: " NAME);
-}
-#endif
diff --git a/elf/tst-initorder2.exp b/elf/tst-initorder2.exp
deleted file mode 100644
index 5169489b85..0000000000
--- a/elf/tst-initorder2.exp
+++ /dev/null
@@ -1,9 +0,0 @@
-init: d
-init: c
-init: b
-init: a
-main
-fini: a
-fini: b
-fini: c
-fini: d
diff --git a/elf/tst-initordera1.c b/elf/tst-initordera1.c
deleted file mode 100644
index f161257142..0000000000
--- a/elf/tst-initordera1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a1( void ) __attribute__((constructor));
-extern void finish_a1( void ) __attribute__((destructor));
-
-void
-start_a1( void )
-{
- printf( "start_a1\n" );
-}
-
-void
-finish_a1( void )
-{
- printf( "finish_a1\n" );
-}
diff --git a/elf/tst-initordera2.c b/elf/tst-initordera2.c
deleted file mode 100644
index a5a9b42ff6..0000000000
--- a/elf/tst-initordera2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a2( void ) __attribute__((constructor));
-extern void finish_a2( void ) __attribute__((destructor));
-
-void
-start_a2( void )
-{
- printf( "start_a2\n" );
-}
-
-void
-finish_a2( void )
-{
- printf( "finish_a2\n" );
-}
diff --git a/elf/tst-initordera3.c b/elf/tst-initordera3.c
deleted file mode 100644
index 1c7f496e9a..0000000000
--- a/elf/tst-initordera3.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a3( void ) __attribute__((constructor));
-extern void finish_a3( void ) __attribute__((destructor));
-
-void
-start_a3( void )
-{
- printf( "start_a3\n" );
-}
-
-void
-finish_a3( void )
-{
- printf( "finish_a3\n" );
-}
diff --git a/elf/tst-initordera4.c b/elf/tst-initordera4.c
deleted file mode 100644
index 70b9f5e392..0000000000
--- a/elf/tst-initordera4.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a4( void ) __attribute__((constructor));
-extern void finish_a4( void ) __attribute__((destructor));
-
-void
-start_a4( void )
-{
- printf( "start_a4\n" );
-}
-
-void
-finish_a4( void )
-{
- printf( "finish_a4\n" );
-}
diff --git a/elf/tst-initorderb1.c b/elf/tst-initorderb1.c
deleted file mode 100644
index 993ea3fe30..0000000000
--- a/elf/tst-initorderb1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_b1( void ) __attribute__((constructor));
-extern void finish_b1( void ) __attribute__((destructor));
-
-void
-start_b1( void )
-{
- printf( "start_b1\n" );
-}
-
-void
-finish_b1( void )
-{
- printf( "finish_b1\n" );
-}
diff --git a/elf/tst-initorderb2.c b/elf/tst-initorderb2.c
deleted file mode 100644
index 3334dda0a9..0000000000
--- a/elf/tst-initorderb2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_b2( void ) __attribute__((constructor));
-extern void finish_b2( void ) __attribute__((destructor));
-
-void
-start_b2( void )
-{
- printf( "start_b2\n" );
-}
-
-void
-finish_b2( void )
-{
- printf( "finish_b2\n" );
-}
diff --git a/elf/tst-latepthread.c b/elf/tst-latepthread.c
deleted file mode 100644
index ca2f82243d..0000000000
--- a/elf/tst-latepthread.c
+++ /dev/null
@@ -1,104 +0,0 @@
-/* Test that loading libpthread does not break ld.so exceptions (bug 16628).
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <signal.h>
-#include <stdio.h>
-#include <string.h>
-#include <sys/wait.h>
-#include <unistd.h>
-
-static int
-do_test (void)
-{
- void *handle = dlopen ("tst-latepthreadmod.so", RTLD_LOCAL | RTLD_LAZY);
- if (handle == NULL)
- {
- printf ("error: dlopen failed: %s\n", dlerror ());
- return 1;
- }
- void *ptr = dlsym (handle, "trigger_dynlink_failure");
- if (ptr == NULL)
- {
- printf ("error: dlsym failed: %s\n", dlerror ());
- return 1;
- }
- int (*func) (void) = ptr;
-
- /* Run the actual test in a subprocess, to capture the error. */
- int fds[2];
- if (pipe (fds) < 0)
- {
- printf ("error: pipe: %m\n");
- return 1;
- }
- pid_t pid = fork ();
- if (pid < 0)
- {
- printf ("error: fork: %m\n");
- return 1;
- }
- else if (pid == 0)
- {
- if (dup2 (fds[1], STDERR_FILENO) < 0)
- _exit (2);
- /* Trigger an abort. */
- func ();
- _exit (3);
- }
- /* NB: This assumes that the abort message is so short that the pipe
- does not block. */
- int status;
- if (waitpid (pid, &status, 0) < 0)
- {
- printf ("error: waitpid: %m\n");
- return 1;
- }
-
- /* Check the printed error message. */
- if (close (fds[1]) < 0)
- {
- printf ("error: close: %m\n");
- return 1;
- }
- char buf[512];
- /* Leave room for the NUL terminator. */
- ssize_t ret = read (fds[0], buf, sizeof (buf) - 1);
- if (ret < 0)
- {
- printf ("error: read: %m\n");
- return 1;
- }
- if (ret > 0 && buf[ret - 1] == '\n')
- --ret;
- buf[ret] = '\0';
- printf ("info: exit status: %d, message: %s\n", status, buf);
- if (strstr (buf, "undefined symbol: this_function_is_not_defined") == NULL)
- {
- printf ("error: message does not contain expected string\n");
- return 1;
- }
- if (!WIFEXITED (status) || WEXITSTATUS (status) != 127)
- {
- printf ("error: unexpected process exit status\n");
- return 1;
- }
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-latepthreadmod.c b/elf/tst-latepthreadmod.c
deleted file mode 100644
index 35a82d388b..0000000000
--- a/elf/tst-latepthreadmod.c
+++ /dev/null
@@ -1,33 +0,0 @@
-/* DSO which links against libpthread and triggers a lazy binding.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file is compiled into a DSO which loads libpthread, but fails
- the dynamic linker afterwards. */
-
-#include <pthread.h>
-
-/* Link in libpthread. */
-void *pthread_create_ptr = &pthread_create;
-
-int this_function_is_not_defined (void);
-
-int
-trigger_dynlink_failure (void)
-{
- return this_function_is_not_defined ();
-}
diff --git a/elf/tst-ldconfig-X.sh b/elf/tst-ldconfig-X.sh
deleted file mode 100644
index e97ca89946..0000000000
--- a/elf/tst-ldconfig-X.sh
+++ /dev/null
@@ -1,62 +0,0 @@
-#!/bin/sh
-# Test that ldconfig -X does not remove stale symbolic links.
-# Copyright (C) 2000-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-set -ex
-
-common_objpfx=$1
-test_wrapper_env=$2
-run_program_env=$3
-
-testroot="${common_objpfx}elf/bug19610-test-directory"
-cleanup () {
- rm -rf "$testroot"
-}
-trap cleanup 0
-
-rm -rf "$testroot"
-mkdir -p $testroot/lib $testroot/etc
-
-# Relative symbolic link target.
-ln -s libdoesnotexist.so.1.1 $testroot/lib/libdoesnotexist.so.1
-
-# Absolute symbolic link target.
-ln -s $testroot/opt/sw/lib/libdoesnotexist2.so.1.1 $testroot/lib/
-
-errors=0
-check_files () {
- for name in libdoesnotexist.so.1 libdoesnotexist2.so.1.1 ; do
- path="$testroot/lib/$name"
- if test ! -h $path ; then
- echo "error: missing file: $path"
- errors=1
- fi
- done
-}
-
-check_files
-
-${test_wrapper_env} \
-${run_program_env} \
-${common_objpfx}elf/ldconfig -X -f /dev/null \
- -C $testroot/etc/ld.so.cache \
- $testroot/lib
-
-check_files
-
-exit $errors
diff --git a/elf/tst-leaks1-static.c b/elf/tst-leaks1-static.c
deleted file mode 100644
index b956d66905..0000000000
--- a/elf/tst-leaks1-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-leaks1.c"
diff --git a/elf/tst-leaks1.c b/elf/tst-leaks1.c
deleted file mode 100644
index d67e8269c4..0000000000
--- a/elf/tst-leaks1.c
+++ /dev/null
@@ -1,27 +0,0 @@
-#include <stdio.h>
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdlib.h>
-
-static int
-do_test (void)
-{
- mtrace ();
-
- int ret = 0;
- for (int i = 0; i < 10; i++)
- {
- void *h = dlopen (i < 5 ? "./tst-leaks1.c"
- : "$ORIGIN/tst-leaks1.o", RTLD_LAZY);
- if (h != NULL)
- {
- puts ("dlopen unexpectedly succeeded");
- ret = 1;
- dlclose (h);
- }
- }
-
- return ret;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-linkall-static.c b/elf/tst-linkall-static.c
deleted file mode 100644
index 8f40657244..0000000000
--- a/elf/tst-linkall-static.c
+++ /dev/null
@@ -1,52 +0,0 @@
-/* Test static linking against multiple libraries, to find symbol conflicts.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public License as
- published by the Free Software Foundation; either version 2.1 of the
- License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; see the file COPYING.LIB. If
- not, see <http://www.gnu.org/licenses/>. */
-
-#include <math.h>
-#include <pthread.h>
-#include <crypt.h>
-#include <resolv.h>
-#include <dlfcn.h>
-#include <utmp.h>
-#include <aio.h>
-#include <netdb.h>
-
-/* These references force linking the executable against central
- functions in the static libraries, pulling significant parts of
- each library into the link. */
-void *references[] =
- {
- &pow, /* libm */
- &pthread_create, /* libpthread */
-#if USE_CRYPT
- &crypt, /* libcrypt */
-#endif
- &res_send, /* libresolv */
- &dlopen, /* libdl */
- &login, /* libutil */
- &aio_init, /* librt */
- &getaddrinfo_a, /* libanl */
- };
-
-static int
-do_test (void)
-{
- /* This is a link-time test. There is nothing to run here. */
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-nodelete-dlclose-dso.c b/elf/tst-nodelete-dlclose-dso.c
deleted file mode 100644
index 4042c78b8a..0000000000
--- a/elf/tst-nodelete-dlclose-dso.c
+++ /dev/null
@@ -1,90 +0,0 @@
-/* Bug 11941: Improper assert map->l_init_called in dlclose.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This is the primary DSO that is loaded by the appliation. This DSO
- then loads a plugin with RTLD_NODELETE. This plugin depends on this
- DSO. This dependency chain means that at application shutdown the
- plugin will be destructed first. Thus by the time this DSO is
- destructed we will be calling dlclose on an object that has already
- been destructed. It is allowed to call dlclose in this way and
- should not assert. */
-#include <stdio.h>
-#include <stdlib.h>
-#include <dlfcn.h>
-
-/* Plugin to load. */
-static void *plugin_lib = NULL;
-/* Plugin function. */
-static void (*plugin_func) (void);
-#define LIB_PLUGIN "tst-nodelete-dlclose-plugin.so"
-
-/* This function is never called but the plugin references it.
- We do this to avoid any future --as-needed from removing the
- plugin's DT_NEEDED on this DSO (required for the test). */
-void
-primary_reference (void)
-{
- printf ("INFO: Called primary_reference function.\n");
-}
-
-void
-primary (void)
-{
- char *error;
-
- plugin_lib = dlopen (LIB_PLUGIN, RTLD_NOW | RTLD_LOCAL | RTLD_NODELETE);
- if (plugin_lib == NULL)
- {
- printf ("ERROR: Unable to load plugin library.\n");
- exit (EXIT_FAILURE);
- }
- dlerror ();
-
- plugin_func = (void (*) (void)) dlsym (plugin_lib, "plugin_func");
- error = dlerror ();
- if (error != NULL)
- {
- printf ("ERROR: Unable to find symbol with error \"%s\".",
- error);
- exit (EXIT_FAILURE);
- }
-
- return;
-}
-
-__attribute__ ((destructor))
-static void
-primary_dtor (void)
-{
- int ret;
-
- printf ("INFO: Calling primary destructor.\n");
-
- /* The destructor runs in the test driver also, which
- hasn't called primary, in that case do nothing. */
- if (plugin_lib == NULL)
- return;
-
- ret = dlclose (plugin_lib);
- if (ret != 0)
- {
- printf ("ERROR: Calling dlclose failed with \"%s\"\n",
- dlerror ());
- exit (EXIT_FAILURE);
- }
-}
diff --git a/elf/tst-nodelete-dlclose-plugin.c b/elf/tst-nodelete-dlclose-plugin.c
deleted file mode 100644
index 00c84d0bc0..0000000000
--- a/elf/tst-nodelete-dlclose-plugin.c
+++ /dev/null
@@ -1,40 +0,0 @@
-/* Bug 11941: Improper assert map->l_init_called in dlclose.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This DSO simulates a plugin with a dependency on the
- primary DSO loaded by the appliation. */
-#include <stdio.h>
-
-extern void primary_reference (void);
-
-void
-plugin_func (void)
-{
- printf ("INFO: Calling plugin function.\n");
- /* Need a reference to the DSO to ensure that a potential --as-needed
- doesn't remove the DT_NEEDED entry which we rely upon to ensure
- destruction ordering. */
- primary_reference ();
-}
-
-__attribute__ ((destructor))
-static void
-plugin_dtor (void)
-{
- printf ("INFO: Calling plugin destructor.\n");
-}
diff --git a/elf/tst-nodelete-dlclose.c b/elf/tst-nodelete-dlclose.c
deleted file mode 100644
index 178673e9d0..0000000000
--- a/elf/tst-nodelete-dlclose.c
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Bug 11941: Improper assert map->l_init_called in dlclose.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This simulates an application using the primary DSO which loads the
- plugin DSO. */
-#include <stdio.h>
-#include <stdlib.h>
-
-extern void primary (void);
-
-static int
-do_test (void)
-{
- printf ("INFO: Starting application.\n");
- primary ();
- printf ("INFO: Exiting application.\n");
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-nodelete-opened-lib.c b/elf/tst-nodelete-opened-lib.c
deleted file mode 100644
index 3e1dcdfc1b..0000000000
--- a/elf/tst-nodelete-opened-lib.c
+++ /dev/null
@@ -1,19 +0,0 @@
-/* Verify that objects opened with RTLD_NODELETE are not unloaded - the DSO.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-int foo_var = 42;
diff --git a/elf/tst-nodelete-opened.c b/elf/tst-nodelete-opened.c
deleted file mode 100644
index d71efa4603..0000000000
--- a/elf/tst-nodelete-opened.c
+++ /dev/null
@@ -1,68 +0,0 @@
-/* Verify that an already opened DSO opened agained with RTLD_NODELETE actually
- sets the NODELETE flag.
-
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-do_test (void)
-{
- void *h1 = dlopen ("$ORIGIN/tst-nodelete-opened-lib.so", RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("h1: failed to open DSO: %s\n", dlerror ());
- return 1;
- }
-
- void *h2 = dlopen ("$ORIGIN/tst-nodelete-opened-lib.so",
- RTLD_LAZY | RTLD_NODELETE);
- if (h2 == NULL)
- {
- printf ("h2: failed to open DSO: %s\n", dlerror ());
- return 1;
- }
-
- int *foo = dlsym (h2, "foo_var");
- if (foo == NULL)
- {
- printf ("failed to load symbol foo_var: %s\n", dlerror ());
- return 1;
- }
-
- if (dlclose (h1) != 0)
- {
- printf ("h1: dlclose failed: %s\n", dlerror ());
- return 1;
- }
-
- if (dlclose (h2) != 0)
- {
- printf ("h2: dlclose failed: %s\n", dlerror ());
- return 1;
- }
-
- /* This FOO dereference will crash with a segfault if the DSO was
- unloaded. */
- printf ("foo == %d\n", *foo);
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-nodelete-rtldmod.cc b/elf/tst-nodelete-rtldmod.cc
deleted file mode 100644
index 740e1d8181..0000000000
--- a/elf/tst-nodelete-rtldmod.cc
+++ /dev/null
@@ -1,6 +0,0 @@
-extern int not_exist (void);
-
-int foo (void)
-{
- return not_exist ();
-}
diff --git a/elf/tst-nodelete-uniquemod.cc b/elf/tst-nodelete-uniquemod.cc
deleted file mode 100644
index 632b303d58..0000000000
--- a/elf/tst-nodelete-uniquemod.cc
+++ /dev/null
@@ -1,14 +0,0 @@
-extern int not_exist (void);
-
-inline int make_unique (void)
-{
- /* Static variables in inline functions and classes
- generate STB_GNU_UNIQUE symbols. */
- static int unique;
- return ++unique;
-}
-
-int foo (void)
-{
- return make_unique () + not_exist ();
-}
diff --git a/elf/tst-nodelete-zmod.cc b/elf/tst-nodelete-zmod.cc
deleted file mode 100644
index 740e1d8181..0000000000
--- a/elf/tst-nodelete-zmod.cc
+++ /dev/null
@@ -1,6 +0,0 @@
-extern int not_exist (void);
-
-int foo (void)
-{
- return not_exist ();
-}
diff --git a/elf/tst-nodelete.cc b/elf/tst-nodelete.cc
deleted file mode 100644
index 5752e7df26..0000000000
--- a/elf/tst-nodelete.cc
+++ /dev/null
@@ -1,50 +0,0 @@
-#include "../dlfcn/dlfcn.h"
-#include <stdio.h>
-#include <stdlib.h>
-
-static int
-do_test (void)
-{
- int result = 0;
-
- /* This is a test for correct handling of dlopen failures for library that
- is loaded with RTLD_NODELETE flag. The first dlopen should fail because
- of undefined symbols in shared library. The second dlopen then verifies
- that library was properly unloaded. */
- if (dlopen ("tst-nodelete-rtldmod.so", RTLD_NOW | RTLD_NODELETE) != NULL
- || dlopen ("tst-nodelete-rtldmod.so", RTLD_LAZY | RTLD_NOLOAD) != NULL)
- {
- printf ("RTLD_NODELETE test failed\n");
- result = 1;
- }
-
- /* This is a test for correct handling of dlopen failures for library that
- is linked with '-z nodelete' option and hence has DF_1_NODELETE flag.
- The first dlopen should fail because of undefined symbols in shared
- library. The second dlopen then verifies that library was properly
- unloaded. */
- if (dlopen ("tst-nodelete-zmod.so", RTLD_NOW) != NULL
- || dlopen ("tst-nodelete-zmod.so", RTLD_LAZY | RTLD_NOLOAD) != NULL)
- {
- printf ("-z nodelete test failed\n");
- result = 1;
- }
-
- /* This is a test for correct handling of dlopen failures for library
- with unique symbols. The first dlopen should fail because of undefined
- symbols in shared library. The second dlopen then verifies that library
- was properly unloaded. */
- if (dlopen ("tst-nodelete-uniquemod.so", RTLD_NOW) != NULL
- || dlopen ("tst-nodelete-uniquemod.so", RTLD_LAZY | RTLD_NOLOAD) != NULL)
- {
- printf ("Unique symbols test failed\n");
- result = 1;
- }
-
- if (result == 0)
- printf ("SUCCESS\n");
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-nodelete2.c b/elf/tst-nodelete2.c
deleted file mode 100644
index 010c4ae237..0000000000
--- a/elf/tst-nodelete2.c
+++ /dev/null
@@ -1,36 +0,0 @@
-#include "../dlfcn/dlfcn.h"
-#include <stdio.h>
-#include <stdlib.h>
-#include <gnu/lib-names.h>
-
-static int
-do_test (void)
-{
- int result = 0;
-
- printf ("\nOpening pthread library.\n");
- void *pthread = dlopen (LIBPTHREAD_SO, RTLD_LAZY);
-
- /* This is a test for correct DF_1_NODELETE clearing when dlopen failure
- happens. We should clear DF_1_NODELETE for failed library only, because
- doing this for others (e.g. libpthread) might cause them to be unloaded,
- that may lead to some global references (e.g. __rtld_lock_unlock) to be
- broken. The dlopen should fail because of undefined symbols in shared
- library, that cause DF_1_NODELETE to be cleared. For libpthread, this
- flag should be set, because if not, SIGSEGV will happen in dlclose. */
- if (dlopen ("tst-nodelete2mod.so", RTLD_NOW) != NULL)
- {
- printf ("Unique symbols test failed\n");
- result = 1;
- }
-
- if (pthread)
- dlclose (pthread);
-
- if (result == 0)
- printf ("SUCCESS\n");
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-nodelete2mod.c b/elf/tst-nodelete2mod.c
deleted file mode 100644
index e88c756f5e..0000000000
--- a/elf/tst-nodelete2mod.c
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Undefined symbol. */
-extern int not_exist (void);
-
-int foo (void)
-{
- return not_exist ();
-}
diff --git a/elf/tst-noload.c b/elf/tst-noload.c
deleted file mode 100644
index 3fb2895e2c..0000000000
--- a/elf/tst-noload.c
+++ /dev/null
@@ -1,72 +0,0 @@
-/* Verify that RTLD_NOLOAD works as expected.
-
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <dlfcn.h>
-#include <stdio.h>
-#include <gnu/lib-names.h>
-
-static int
-do_test (void)
-{
- /* Test that no object is loaded with RTLD_NOLOAD. */
- void *h1 = dlopen (LIBM_SO, RTLD_LAZY | RTLD_NOLOAD);
- if (h1 != NULL)
- {
- printf ("h1: DSO has been loaded while it should have not\n");
- return 1;
- }
-
- /* This used to segfault in some glibc versions. */
- void *h2 = dlopen (LIBM_SO, RTLD_LAZY | RTLD_NOLOAD | RTLD_NODELETE);
- if (h2 != NULL)
- {
- printf ("h2: DSO has been loaded while it should have not\n");
- return 1;
- }
-
- /* Test that loading an already loaded object returns the same. */
- void *h3 = dlopen (LIBM_SO, RTLD_LAZY);
- if (h3 == NULL)
- {
- printf ("h3: failed to open DSO: %s\n", dlerror ());
- return 1;
- }
- void *h4 = dlopen (LIBM_SO, RTLD_LAZY | RTLD_NOLOAD);
- if (h4 == NULL)
- {
- printf ("h4: failed to open DSO: %s\n", dlerror ());
- return 1;
- }
- if (h4 != h3)
- {
- printf ("h4: should return the same object\n");
- return 1;
- }
-
- /* Cleanup */
- if (dlclose (h3) != 0)
- {
- printf ("h3: dlclose failed: %s\n", dlerror ());
- return 1;
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-null-argv-lib.c b/elf/tst-null-argv-lib.c
deleted file mode 100644
index 12af03ba95..0000000000
--- a/elf/tst-null-argv-lib.c
+++ /dev/null
@@ -1,24 +0,0 @@
-/* Verify that program does not crash when LD_DEBUG is set and the program name
- is not available. This is the library.
- Copyright (C) 2013-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-void
-foo (void)
-{
- return;
-}
diff --git a/elf/tst-null-argv.c b/elf/tst-null-argv.c
deleted file mode 100644
index 21b87327c1..0000000000
--- a/elf/tst-null-argv.c
+++ /dev/null
@@ -1,36 +0,0 @@
-/* Verify that program does not crash when LD_DEBUG is set and the program name
- is not available.
- Copyright (C) 2013-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-extern void foo (void);
-
-int
-do_test (int argc, char **argv)
-{
- argv[0] = argv[1];
- argc--;
-
- /* This should result in a symbol lookup, causing a volley of debug output
- when LD_DEBUG=symbols. */
- foo ();
-
- return 0;
-}
-
-#define TEST_FUNCTION_ARGV do_test
-#include <support/test-driver.c>
diff --git a/elf/tst-order-a1.c b/elf/tst-order-a1.c
deleted file mode 100644
index f161257142..0000000000
--- a/elf/tst-order-a1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a1( void ) __attribute__((constructor));
-extern void finish_a1( void ) __attribute__((destructor));
-
-void
-start_a1( void )
-{
- printf( "start_a1\n" );
-}
-
-void
-finish_a1( void )
-{
- printf( "finish_a1\n" );
-}
diff --git a/elf/tst-order-a2.c b/elf/tst-order-a2.c
deleted file mode 100644
index a5a9b42ff6..0000000000
--- a/elf/tst-order-a2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a2( void ) __attribute__((constructor));
-extern void finish_a2( void ) __attribute__((destructor));
-
-void
-start_a2( void )
-{
- printf( "start_a2\n" );
-}
-
-void
-finish_a2( void )
-{
- printf( "finish_a2\n" );
-}
diff --git a/elf/tst-order-a3.c b/elf/tst-order-a3.c
deleted file mode 100644
index 1c7f496e9a..0000000000
--- a/elf/tst-order-a3.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a3( void ) __attribute__((constructor));
-extern void finish_a3( void ) __attribute__((destructor));
-
-void
-start_a3( void )
-{
- printf( "start_a3\n" );
-}
-
-void
-finish_a3( void )
-{
- printf( "finish_a3\n" );
-}
diff --git a/elf/tst-order-a4.c b/elf/tst-order-a4.c
deleted file mode 100644
index 70b9f5e392..0000000000
--- a/elf/tst-order-a4.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_a4( void ) __attribute__((constructor));
-extern void finish_a4( void ) __attribute__((destructor));
-
-void
-start_a4( void )
-{
- printf( "start_a4\n" );
-}
-
-void
-finish_a4( void )
-{
- printf( "finish_a4\n" );
-}
diff --git a/elf/tst-order-b1.c b/elf/tst-order-b1.c
deleted file mode 100644
index 993ea3fe30..0000000000
--- a/elf/tst-order-b1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_b1( void ) __attribute__((constructor));
-extern void finish_b1( void ) __attribute__((destructor));
-
-void
-start_b1( void )
-{
- printf( "start_b1\n" );
-}
-
-void
-finish_b1( void )
-{
- printf( "finish_b1\n" );
-}
diff --git a/elf/tst-order-b2.c b/elf/tst-order-b2.c
deleted file mode 100644
index 3334dda0a9..0000000000
--- a/elf/tst-order-b2.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-extern void start_b2( void ) __attribute__((constructor));
-extern void finish_b2( void ) __attribute__((destructor));
-
-void
-start_b2( void )
-{
- printf( "start_b2\n" );
-}
-
-void
-finish_b2( void )
-{
- printf( "finish_b2\n" );
-}
diff --git a/elf/tst-order-main.c b/elf/tst-order-main.c
deleted file mode 100644
index 2a90130db6..0000000000
--- a/elf/tst-order-main.c
+++ /dev/null
@@ -1,12 +0,0 @@
-#include <stdio.h>
-#include <unistd.h>
-#include <stdlib.h>
-
-static int
-do_test (void)
-{
- printf( "main\n" );
- exit(EXIT_SUCCESS);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-pathopt.c b/elf/tst-pathopt.c
deleted file mode 100644
index e2c96fbc72..0000000000
--- a/elf/tst-pathopt.c
+++ /dev/null
@@ -1,41 +0,0 @@
-#include <dlfcn.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-static int
-do_test (void)
-{
- void *h;
- int (*fp) (int);
- int result;
-
- mtrace ();
-
- h = dlopen ("renamed.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("failed to load \"%s\": %s\n", "renamed.so", dlerror ());
- exit (1);
- }
-
- fp = dlsym (h, "in_renamed");
- if (fp == NULL)
- {
- printf ("lookup of \"%s\" failed: %s\n", "in_renamed", dlerror ());
- exit (1);
- }
-
- result = fp (10);
-
- if (dlclose (h) != 0)
- {
- printf ("failed to close \"%s\": %s\n", "renamed.so", dlerror ());
- exit (1);
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-pathopt.sh b/elf/tst-pathopt.sh
deleted file mode 100755
index 4183a697dc..0000000000
--- a/elf/tst-pathopt.sh
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/bin/sh
-# Test lookup path optimization.
-# Copyright (C) 2000-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-set -e
-
-common_objpfx=$1
-test_wrapper_env=$2
-run_program_env=$3
-
-test -e ${common_objpfx}elf/will-be-empty &&
- rm -fr ${common_objpfx}elf/will-be-empty
-test -d ${common_objpfx}elf/for-renamed ||
- mkdir ${common_objpfx}elf/for-renamed
-
-cp ${common_objpfx}elf/pathoptobj.so ${common_objpfx}elf/for-renamed/renamed.so
-
-${test_wrapper_env} \
-${run_program_env} \
-LD_LIBRARY_PATH=${common_objpfx}elf/will-be-empty:${common_objpfx}elf/for-renamed:${common_objpfx}.:${common_objpfx}dlfcn \
- ${common_objpfx}elf/ld.so ${common_objpfx}elf/tst-pathopt \
- > ${common_objpfx}elf/tst-pathopt.out
-
-exit $?
diff --git a/elf/tst-pie1.c b/elf/tst-pie1.c
deleted file mode 100644
index 75d941f21f..0000000000
--- a/elf/tst-pie1.c
+++ /dev/null
@@ -1,5 +0,0 @@
-int
-foo (void)
-{
- return 34;
-}
diff --git a/elf/tst-pie2.c b/elf/tst-pie2.c
deleted file mode 100644
index 32943bbc1a..0000000000
--- a/elf/tst-pie2.c
+++ /dev/null
@@ -1,40 +0,0 @@
-/* Test case for BZ #16381
-
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-
-#include <assert.h>
-
-static int g;
-
-void init_g (void) __attribute__((constructor));
-
-void
-init_g (void)
-{
- assert (g == 0);
- g += 1;
-}
-
-static int
-do_test (void)
-{
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-piemod1.c b/elf/tst-piemod1.c
deleted file mode 100644
index 72d7e0a187..0000000000
--- a/elf/tst-piemod1.c
+++ /dev/null
@@ -1,22 +0,0 @@
-#include <stdio.h>
-
-int
-foo (void)
-{
- return 21;
-}
-
-static int
-do_test (void)
-{
- int val = foo ();
- if (val != 34)
- {
- printf ("foo () returned %d\n", val);
- return 1;
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-prelink.c b/elf/tst-prelink.c
deleted file mode 100644
index 7435c321d3..0000000000
--- a/elf/tst-prelink.c
+++ /dev/null
@@ -1,29 +0,0 @@
-/* Test the output from the environment variable, LD_TRACE_PRELINKING,
- for prelink.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- fprintf (stdout, "hello\n");
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-prelink.exp b/elf/tst-prelink.exp
deleted file mode 100644
index b35b4c9705..0000000000
--- a/elf/tst-prelink.exp
+++ /dev/null
@@ -1 +0,0 @@
-/0 stdout
diff --git a/elf/tst-protected1a.c b/elf/tst-protected1a.c
deleted file mode 100644
index 4267b951c4..0000000000
--- a/elf/tst-protected1a.c
+++ /dev/null
@@ -1,234 +0,0 @@
-/* Test the protected visibility when main is linked with moda and modb
- in that order:
- 1. Protected symbols, protected1, protected2 and protected3, defined
- in moda, are used in moda.
- 2. Protected symbol, protected3, defined in modb, are used in modb.
- 3. Symbol, protected1, defined in moda, is also used in main and modb.
- 4. Symbol, protected2, defined in main, is used in main.
- 5. Symbol, protected3, defined in moda, is also used in main.
-
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file must be compiled as PIE to avoid copy relocation when
- accessing protected symbols defined in shared libaries since copy
- relocation doesn't work with protected symbols and linker in
- binutils 2.26 enforces this rule. */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "tst-protected1mod.h"
-
-/* Prototype for our test function. */
-extern int do_test (void);
-
-int protected2 = -1;
-
-/* This defines the `main' function and some more. */
-#include <support/test-driver.c>
-
-int
-do_test (void)
-{
- int res = 0;
-
- /* Check if we get the same address for the protected data symbol. */
- if (&protected1 != protected1a_p ())
- {
- puts ("`protected1' in main and moda doesn't have same address");
- res = 1;
- }
- if (&protected1 != protected1b_p ())
- {
- puts ("`protected1' in main and modb doesn't have same address");
- res = 1;
- }
-
- /* Check if we get the right value for the protected data symbol. */
- if (protected1 != 3)
- {
- puts ("`protected1' in main and moda doesn't have same value");
- res = 1;
- }
-
- /* Check if we get the right value for data defined in executable. */
- if (protected2 != -1)
- {
- puts ("`protected2' in main has the wrong value");
- res = 1;
- }
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the same address for the protected data symbol. */
- if (&protected3 != protected3a_p ())
- {
- puts ("`protected3' in main and moda doesn't have same address");
- res = 1;
- }
- if (&protected3 == protected3b_p ())
- {
- puts ("`protected3' in main and modb has same address");
- res = 1;
- }
-
- /* Check if we get the right value for the protected data symbol. */
- if (protected3 != 5)
- {
- puts ("`protected3' in main and moda doesn't have same value");
- res = 1;
- }
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- /* Set `protected2' in moda to 30. */
- set_protected2 (300);
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Set `protected1' in moda to 30. */
- set_protected1a (30);
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected1 != 30)
- {
- puts ("`protected1' in main doesn't have the updated value");
- res = 1;
- }
-
- protected2 = -300;
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if data defined in executable is changed. */
- if (protected2 != -300)
- {
- puts ("`protected2' in main is changed");
- res = 1;
- }
-
- /* Set `protected1' in modb to 40. */
- set_protected1b (40);
- set_expected_protected1 (40);
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected1 != 40)
- {
- puts ("`protected1' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Set `protected3' in moda to 80. */
- set_protected3a (80);
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected3 != 80)
- {
- puts ("`protected3' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- /* Set `protected3' in modb to 100. */
- set_protected3b (100);
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected3 != 80)
- {
- puts ("`protected3' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- return res;
-}
diff --git a/elf/tst-protected1b.c b/elf/tst-protected1b.c
deleted file mode 100644
index 9fd695bffa..0000000000
--- a/elf/tst-protected1b.c
+++ /dev/null
@@ -1,240 +0,0 @@
-/* Test the protected visibility when main is linked with modb and moda
- in that order:
- 1. Protected symbols, protected1, protected2 and protected3, defined
- in moda, are used in moda.
- 2. Protected symbol, protected3, defined in modb, are used in modb
- 3. Symbol, protected1, defined in modb, is used in main and modb.
- 4. Symbol, protected2, defined in main, is used in main.
- 5. Symbol, protected3, defined in modb, is also used in main.
-
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file must be compiled as PIE to avoid copy relocation when
- accessing protected symbols defined in shared libaries since copy
- relocation doesn't work with protected symbols and linker in
- binutils 2.26 enforces this rule. */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "tst-protected1mod.h"
-
-/* Prototype for our test function. */
-extern int do_test (void);
-
-int protected2 = -1;
-
-/* This defines the `main' function and some more. */
-#include <support/test-driver.c>
-
-int
-do_test (void)
-{
- int res = 0;
-
- /* Check if we get the same address for the protected data symbol. */
- if (&protected1 == protected1a_p ())
- {
- puts ("`protected1' in main and moda has same address");
- res = 1;
- }
- if (&protected1 != protected1b_p ())
- {
- puts ("`protected1' in main and modb doesn't have same address");
- res = 1;
- }
-
- /* Check if we get the right value for the protected data symbol. */
- if (protected1 != -3)
- {
- puts ("`protected1' in main and modb doesn't have same value");
- res = 1;
- }
-
- /* Check if we get the right value for data defined in executable. */
- if (protected2 != -1)
- {
- puts ("`protected2' in main has the wrong value");
- res = 1;
- }
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the same address for the protected data symbol. */
- if (&protected3 == protected3a_p ())
- {
- puts ("`protected3' in main and moda has same address");
- res = 1;
- }
- if (&protected3 != protected3b_p ())
- {
- puts ("`protected3' in main and modb doesn't have same address");
- res = 1;
- }
-
- /* Check if we get the right value for the protected data symbol. */
- if (protected3 != -5)
- {
- puts ("`protected3' in main and modb doesn't have same value");
- res = 1;
- }
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- /* Set `protected2' in moda to 30. */
- set_protected2 (300);
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the right value for data defined in executable. */
- if (protected2 != -1)
- {
- puts ("`protected2' in main has the wrong value");
- res = 1;
- }
-
- /* Set `protected1' in moda to 30. */
- set_protected1a (30);
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the same value for the protected data symbol. */
- if (protected1 != -3)
- {
- puts ("`protected1' in main has the wrong value");
- res = 1;
- }
-
- protected2 = -300;
-
- /* Check `protected2' in moda. */
- if (!check_protected2 ())
- {
- puts ("`protected2' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if data defined in executable is changed. */
- if (protected2 != -300)
- {
- puts ("`protected2' in main is changed");
- res = 1;
- }
-
- /* Set `protected1' in modb to 40. */
- set_protected1b (40);
-
- /* Check `protected1' in moda. */
- if (!check_protected1 ())
- {
- puts ("`protected1' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected1 != 40)
- {
- puts ("`protected1' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Set `protected3' in moda to 80. */
- set_protected3a (80);
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected3 != -5)
- {
- puts ("`protected3' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- /* Set `protected3' in modb to 100. */
- set_protected3b (100);
-
- /* Check `protected3' in moda. */
- if (!check_protected3a ())
- {
- puts ("`protected3' in moda has the wrong value");
- res = 1;
- }
-
- /* Check if we get the updated value for the protected data symbol. */
- if (protected3 != 100)
- {
- puts ("`protected3' in main doesn't have the updated value");
- res = 1;
- }
-
- /* Check `protected3' in modb. */
- if (!check_protected3b ())
- {
- puts ("`protected3' in modb has the wrong value");
- res = 1;
- }
-
- return res;
-}
diff --git a/elf/tst-protected1mod.h b/elf/tst-protected1mod.h
deleted file mode 100644
index a47d65f6b1..0000000000
--- a/elf/tst-protected1mod.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/* Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Prototypes for the functions in the DSOs. */
-extern int protected1;
-extern int protected2;
-extern int protected3;
-
-extern void set_protected1a (int);
-extern void set_protected1b (int);
-extern int *protected1a_p (void);
-extern int *protected1b_p (void);
-
-extern void set_expected_protected1 (int);
-extern int check_protected1 (void);
-
-extern void set_protected2 (int);
-extern int check_protected2 (void);
-
-extern void set_expected_protected3a (int);
-extern void set_protected3a (int);
-extern int check_protected3a (void);
-extern int *protected3a_p (void);
-extern void set_expected_protected3b (int);
-extern void set_protected3b (int);
-extern int check_protected3b (void);
-extern int *protected3b_p (void);
diff --git a/elf/tst-protected1moda.c b/elf/tst-protected1moda.c
deleted file mode 100644
index aca4fc82a8..0000000000
--- a/elf/tst-protected1moda.c
+++ /dev/null
@@ -1,92 +0,0 @@
-/* Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "tst-protected1mod.h"
-
-int protected1 = 3;
-static int expected_protected1 = 3;
-int protected2 = 4;
-static int expected_protected2 = 4;
-int protected3 = 5;
-static int expected_protected3 = 5;
-
-asm (".protected protected1");
-asm (".protected protected2");
-asm (".protected protected3");
-
-void
-set_protected1a (int i)
-{
- protected1 = i;
- set_expected_protected1 (i);
-}
-
-void
-set_expected_protected1 (int i)
-{
- expected_protected1 = i;
-}
-
-int *
-protected1a_p (void)
-{
- return &protected1;
-}
-
-int
-check_protected1 (void)
-{
- return protected1 == expected_protected1;
-}
-
-void
-set_protected2 (int i)
-{
- protected2 = i;
- expected_protected2 = i;
-}
-
-int
-check_protected2 (void)
-{
- return protected2 == expected_protected2;
-}
-
-void
-set_expected_protected3a (int i)
-{
- expected_protected3 = i;
-}
-
-void
-set_protected3a (int i)
-{
- protected3 = i;
- set_expected_protected3a (i);
-}
-
-int
-check_protected3a (void)
-{
- return protected3 == expected_protected3;
-}
-
-int *
-protected3a_p (void)
-{
- return &protected3;
-}
diff --git a/elf/tst-protected1modb.c b/elf/tst-protected1modb.c
deleted file mode 100644
index 5036b6c3e7..0000000000
--- a/elf/tst-protected1modb.c
+++ /dev/null
@@ -1,62 +0,0 @@
-/* Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdlib.h>
-#include "tst-protected1mod.h"
-
-int protected1 = -3;
-int protected3 = -5;
-static int expected_protected3 = -5;
-
-asm (".protected protected3");
-
-void
-set_protected1b (int i)
-{
- protected1 = i;
-}
-
-int *
-protected1b_p (void)
-{
- return &protected1;
-}
-
-void
-set_expected_protected3b (int i)
-{
- expected_protected3 = i;
-}
-
-void
-set_protected3b (int i)
-{
- protected3 = i;
- set_expected_protected3b (i);
-}
-
-int
-check_protected3b (void)
-{
- return protected3 == expected_protected3;
-}
-
-int *
-protected3b_p (void)
-{
- return &protected3;
-}
diff --git a/elf/tst-ptrguard1-static.c b/elf/tst-ptrguard1-static.c
deleted file mode 100644
index 7aff3b7b5d..0000000000
--- a/elf/tst-ptrguard1-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-ptrguard1.c"
diff --git a/elf/tst-ptrguard1.c b/elf/tst-ptrguard1.c
deleted file mode 100644
index 8ea65bb0bb..0000000000
--- a/elf/tst-ptrguard1.c
+++ /dev/null
@@ -1,217 +0,0 @@
-/* Copyright (C) 2013-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <sys/wait.h>
-#include <stackguard-macros.h>
-#include <tls.h>
-#include <unistd.h>
-
-#ifndef _GNU_SOURCE
-#define _GNU_SOURCE
-#endif
-/* Requires _GNU_SOURCE */
-#include <getopt.h>
-
-#ifndef POINTER_CHK_GUARD
-extern uintptr_t __pointer_chk_guard;
-# define POINTER_CHK_GUARD __pointer_chk_guard
-#endif
-
-static const char *command;
-static bool child;
-static uintptr_t ptr_chk_guard_copy;
-static bool ptr_chk_guard_copy_set;
-static int fds[2];
-
-static void __attribute__ ((constructor))
-con (void)
-{
- ptr_chk_guard_copy = POINTER_CHK_GUARD;
- ptr_chk_guard_copy_set = true;
-}
-
-static int
-uintptr_t_cmp (const void *a, const void *b)
-{
- if (*(uintptr_t *) a < *(uintptr_t *) b)
- return 1;
- if (*(uintptr_t *) a > *(uintptr_t *) b)
- return -1;
- return 0;
-}
-
-static int
-do_test (void)
-{
- if (!ptr_chk_guard_copy_set)
- {
- puts ("constructor has not been run");
- return 1;
- }
-
- if (ptr_chk_guard_copy != POINTER_CHK_GUARD)
- {
- puts ("POINTER_CHK_GUARD changed between constructor and do_test");
- return 1;
- }
-
- if (child)
- {
- write (2, &ptr_chk_guard_copy, sizeof (ptr_chk_guard_copy));
- return 0;
- }
-
- if (command == NULL)
- {
- puts ("missing --command or --child argument");
- return 1;
- }
-
-#define N 16
- uintptr_t child_ptr_chk_guards[N + 1];
- child_ptr_chk_guards[N] = ptr_chk_guard_copy;
- int i;
- for (i = 0; i < N; ++i)
- {
- if (pipe (fds) < 0)
- {
- printf ("couldn't create pipe: %m\n");
- return 1;
- }
-
- pid_t pid = fork ();
- if (pid < 0)
- {
- printf ("fork failed: %m\n");
- return 1;
- }
-
- if (!pid)
- {
- if (ptr_chk_guard_copy != POINTER_CHK_GUARD)
- {
- puts ("POINTER_CHK_GUARD changed after fork");
- exit (1);
- }
-
- close (fds[0]);
- close (2);
- dup2 (fds[1], 2);
- close (fds[1]);
-
- system (command);
- exit (0);
- }
-
- close (fds[1]);
-
- if (TEMP_FAILURE_RETRY (read (fds[0], &child_ptr_chk_guards[i],
- sizeof (uintptr_t))) != sizeof (uintptr_t))
- {
- puts ("could not read ptr_chk_guard value from child");
- return 1;
- }
-
- close (fds[0]);
-
- pid_t termpid;
- int status;
- termpid = TEMP_FAILURE_RETRY (waitpid (pid, &status, 0));
- if (termpid == -1)
- {
- printf ("waitpid failed: %m\n");
- return 1;
- }
- else if (termpid != pid)
- {
- printf ("waitpid returned %ld != %ld\n",
- (long int) termpid, (long int) pid);
- return 1;
- }
- else if (!WIFEXITED (status) || WEXITSTATUS (status))
- {
- puts ("child hasn't exited with exit status 0");
- return 1;
- }
- }
-
- qsort (child_ptr_chk_guards, N + 1, sizeof (uintptr_t), uintptr_t_cmp);
-
- /* The default pointer guard is the same as the default stack guard.
- They are only set to default if dl_random is NULL. */
- uintptr_t default_guard = 0;
- unsigned char *p = (unsigned char *) &default_guard;
- p[sizeof (uintptr_t) - 1] = 255;
- p[sizeof (uintptr_t) - 2] = '\n';
- p[0] = 0;
-
- /* Test if the pointer guard canaries are either randomized,
- or equal to the default pointer guard value.
- Even with randomized pointer guards it might happen
- that the random number generator generates the same
- values, but if that happens in more than half from
- the 16 runs, something is very wrong. */
- int ndifferences = 0;
- int ndefaults = 0;
- for (i = 0; i < N; ++i)
- {
- if (child_ptr_chk_guards[i] != child_ptr_chk_guards[i+1])
- ndifferences++;
- else if (child_ptr_chk_guards[i] == default_guard)
- ndefaults++;
- }
-
- printf ("differences %d defaults %d\n", ndifferences, ndefaults);
-
- if (ndifferences < N / 2 && ndefaults < N / 2)
- {
- puts ("pointer guard values are not randomized enough");
- puts ("nor equal to the default value");
- return 1;
- }
-
- return 0;
-}
-
-#define OPT_COMMAND 10000
-#define OPT_CHILD 10001
-#define CMDLINE_OPTIONS \
- { "command", required_argument, NULL, OPT_COMMAND }, \
- { "child", no_argument, NULL, OPT_CHILD },
-
-static void __attribute((used))
-cmdline_process_function (int c)
-{
- switch (c)
- {
- case OPT_COMMAND:
- command = optarg;
- break;
- case OPT_CHILD:
- child = true;
- break;
- }
-}
-
-#define CMDLINE_PROCESS cmdline_process_function
-
-#include <support/test-driver.c>
diff --git a/elf/tst-relsort1.c b/elf/tst-relsort1.c
deleted file mode 100644
index 775c968e1f..0000000000
--- a/elf/tst-relsort1.c
+++ /dev/null
@@ -1,18 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-
-static int
-do_test (void)
-{
- const char lib[] = "$ORIGIN/tst-relsort1mod1.so";
- void *h = dlopen (lib, RTLD_NOW);
- if (h == NULL)
- {
- puts (dlerror ());
- return 1;
- }
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-relsort1mod1.c b/elf/tst-relsort1mod1.c
deleted file mode 100644
index 9e4a94321d..0000000000
--- a/elf/tst-relsort1mod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern int foo (double);
-
-int
-bar (void)
-{
- return foo (1.2);
-}
diff --git a/elf/tst-relsort1mod2.c b/elf/tst-relsort1mod2.c
deleted file mode 100644
index a2c3e551e4..0000000000
--- a/elf/tst-relsort1mod2.c
+++ /dev/null
@@ -1,7 +0,0 @@
-#include <math.h>
-
-int
-foo (double d)
-{
- return floor (d) != 0.0;
-}
diff --git a/elf/tst-rtld-load-self.sh b/elf/tst-rtld-load-self.sh
deleted file mode 100755
index e05f6d145f..0000000000
--- a/elf/tst-rtld-load-self.sh
+++ /dev/null
@@ -1,49 +0,0 @@
-#!/bin/sh
-# Test how rtld loads itself.
-# Copyright (C) 2012-2017 Free Software Foundation, Inc.
-# This file is part of the GNU C Library.
-#
-
-# The GNU C Library is free software; you can redistribute it and/or
-# modify it under the terms of the GNU Lesser General Public
-# License as published by the Free Software Foundation; either
-# version 2.1 of the License, or (at your option) any later version.
-
-# The GNU C Library is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# Lesser General Public License for more details.
-
-# You should have received a copy of the GNU Lesser General Public
-# License along with the GNU C Library; if not, see
-# <http://www.gnu.org/licenses/>.
-
-set -e
-
-rtld=$1
-test_wrapper=$2
-test_wrapper_env=$3
-result=0
-
-echo '# normal mode'
-${test_wrapper} $rtld $rtld 2>&1 && rc=0 || rc=$?
-echo "# exit status $rc"
-test $rc -le 127 || result=1
-
-echo '# list mode'
-${test_wrapper} $rtld --list $rtld 2>&1 && rc=0 || rc=$?
-echo "# exit status $rc"
-test $rc -eq 0 || result=1
-
-echo '# verify mode'
-${test_wrapper} $rtld --verify $rtld 2>&1 && rc=0 || rc=$?
-echo "# exit status $rc"
-test $rc -eq 2 || result=1
-
-echo '# trace mode'
-${test_wrapper_env} LD_TRACE_LOADED_OBJECTS=1 \
- $rtld $rtld 2>&1 && rc=0 || rc=$?
-echo "# exit status $rc"
-test $rc -eq 0 || result=1
-
-exit $result
diff --git a/elf/tst-stackguard1-static.c b/elf/tst-stackguard1-static.c
deleted file mode 100644
index db1e21554d..0000000000
--- a/elf/tst-stackguard1-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-stackguard1.c"
diff --git a/elf/tst-stackguard1.c b/elf/tst-stackguard1.c
deleted file mode 100644
index 78e33c7083..0000000000
--- a/elf/tst-stackguard1.c
+++ /dev/null
@@ -1,205 +0,0 @@
-/* Copyright (C) 2005-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
- Contributed by Jakub Jelinek <jakub@redhat.com>, 2005.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <errno.h>
-#include <getopt.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <sys/wait.h>
-#include <stackguard-macros.h>
-#include <tls.h>
-#include <unistd.h>
-
-static const char *command;
-static bool child;
-static uintptr_t stack_chk_guard_copy;
-static bool stack_chk_guard_copy_set;
-static int fds[2];
-
-static void __attribute__ ((constructor))
-con (void)
-{
- stack_chk_guard_copy = STACK_CHK_GUARD;
- stack_chk_guard_copy_set = true;
-}
-
-static int
-uintptr_t_cmp (const void *a, const void *b)
-{
- if (*(uintptr_t *) a < *(uintptr_t *) b)
- return 1;
- if (*(uintptr_t *) a > *(uintptr_t *) b)
- return -1;
- return 0;
-}
-
-static int
-do_test (void)
-{
- if (!stack_chk_guard_copy_set)
- {
- puts ("constructor has not been run");
- return 1;
- }
-
- if (stack_chk_guard_copy != STACK_CHK_GUARD)
- {
- puts ("STACK_CHK_GUARD changed between constructor and do_test");
- return 1;
- }
-
- if (child)
- {
- write (2, &stack_chk_guard_copy, sizeof (stack_chk_guard_copy));
- return 0;
- }
-
- if (command == NULL)
- {
- puts ("missing --command or --child argument");
- return 1;
- }
-
-#define N 16
- uintptr_t child_stack_chk_guards[N + 1];
- child_stack_chk_guards[N] = stack_chk_guard_copy;
- int i;
- for (i = 0; i < N; ++i)
- {
- if (pipe (fds) < 0)
- {
- printf ("couldn't create pipe: %m\n");
- return 1;
- }
-
- pid_t pid = fork ();
- if (pid < 0)
- {
- printf ("fork failed: %m\n");
- return 1;
- }
-
- if (!pid)
- {
- if (stack_chk_guard_copy != STACK_CHK_GUARD)
- {
- puts ("STACK_CHK_GUARD changed after fork");
- exit (1);
- }
-
- close (fds[0]);
- close (2);
- dup2 (fds[1], 2);
- close (fds[1]);
-
- system (command);
- exit (0);
- }
-
- close (fds[1]);
-
- if (TEMP_FAILURE_RETRY (read (fds[0], &child_stack_chk_guards[i],
- sizeof (uintptr_t))) != sizeof (uintptr_t))
- {
- puts ("could not read stack_chk_guard value from child");
- return 1;
- }
-
- close (fds[0]);
-
- pid_t termpid;
- int status;
- termpid = TEMP_FAILURE_RETRY (waitpid (pid, &status, 0));
- if (termpid == -1)
- {
- printf ("waitpid failed: %m\n");
- return 1;
- }
- else if (termpid != pid)
- {
- printf ("waitpid returned %ld != %ld\n",
- (long int) termpid, (long int) pid);
- return 1;
- }
- else if (!WIFEXITED (status) || WEXITSTATUS (status))
- {
- puts ("child hasn't exited with exit status 0");
- return 1;
- }
- }
-
- qsort (child_stack_chk_guards, N + 1, sizeof (uintptr_t), uintptr_t_cmp);
-
- uintptr_t default_guard = 0;
- unsigned char *p = (unsigned char *) &default_guard;
- p[sizeof (uintptr_t) - 1] = 255;
- p[sizeof (uintptr_t) - 2] = '\n';
- p[0] = 0;
-
- /* Test if the stack guard canaries are either randomized,
- or equal to the default stack guard canary value.
- Even with randomized stack guards it might happen
- that the random number generator generates the same
- values, but if that happens in more than half from
- the 16 runs, something is very wrong. */
- int ndifferences = 0;
- int ndefaults = 0;
- for (i = 0; i < N; ++i)
- {
- if (child_stack_chk_guards[i] != child_stack_chk_guards[i+1])
- ndifferences++;
- else if (child_stack_chk_guards[i] == default_guard)
- ndefaults++;
- }
-
- printf ("differences %d defaults %d\n", ndifferences, ndefaults);
-
- if (ndifferences < N / 2 && ndefaults < N / 2)
- {
- puts ("stack guard canaries are not randomized enough");
- puts ("nor equal to the default canary value");
- return 1;
- }
-
- return 0;
-}
-
-#define OPT_COMMAND 10000
-#define OPT_CHILD 10001
-#define CMDLINE_OPTIONS \
- { "command", required_argument, NULL, OPT_COMMAND }, \
- { "child", no_argument, NULL, OPT_CHILD },
-
-static void __attribute__((used))
-cmdline_process_function (int c)
-{
- switch (c)
- {
- case OPT_COMMAND:
- command = optarg;
- break;
- case OPT_CHILD:
- child = true;
- break;
- }
-}
-#define CMDLINE_PROCESS cmdline_process_function
-
-#include <support/test-driver.c>
diff --git a/elf/tst-thrlock.c b/elf/tst-thrlock.c
deleted file mode 100644
index 1beffc3861..0000000000
--- a/elf/tst-thrlock.c
+++ /dev/null
@@ -1,58 +0,0 @@
-#include <dlfcn.h>
-#include <pthread.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <gnu/lib-names.h>
-
-static void *
-tf (void *arg)
-{
- void *h = dlopen (LIBM_SO, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("dlopen failed: %s\n", dlerror ());
- exit (1);
- }
- if (dlsym (h, "sin") == NULL)
- {
- printf ("dlsym failed: %s\n", dlerror ());
- exit (1);
- }
- if (dlclose (h) != 0)
- {
- printf ("dlclose failed: %s\n", dlerror ());
- exit (1);
- }
- return NULL;
-}
-
-
-static int
-do_test (void)
-{
-#define N 10
- pthread_t th[N];
- for (int i = 0; i < N; ++i)
- {
- int e = pthread_create (&th[i], NULL, tf, NULL);
- if (e != 0)
- {
- printf ("pthread_create failed with %d (%s)\n", e, strerror (e));
- return 1;
- }
- }
- for (int i = 0; i < N; ++i)
- {
- void *res;
- int e = pthread_join (th[i], &res);
- if (e != 0 || res != NULL)
- {
- puts ("thread failed");
- return 1;
- }
- }
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls-dlinfo.c b/elf/tst-tls-dlinfo.c
deleted file mode 100644
index 7d2b42e2ab..0000000000
--- a/elf/tst-tls-dlinfo.c
+++ /dev/null
@@ -1,85 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-tlsmod2.so";
- int result = 0;
- int *foop;
- int (*fp) (int, int *);
- void *h;
-
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- fp = dlsym (h, "in_dso");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso': %s\n", dlerror ());
- exit (1);
- }
-
- size_t modid = -1;
- if (dlinfo (h, RTLD_DI_TLS_MODID, &modid))
- {
- printf ("dlinfo RTLD_DI_TLS_MODID failed: %s\n", dlerror ());
- result = 1;
- }
- else
- printf ("dlinfo says TLS module ID %Zu\n", modid);
-
- void *block;
- if (dlinfo (h, RTLD_DI_TLS_DATA, &block))
- {
- printf ("dlinfo RTLD_DI_TLS_DATA failed: %s\n", dlerror ());
- result = 1;
- }
- else if (block != NULL)
- {
- printf ("dlinfo RTLD_DI_TLS_DATA says %p but should be unallocated\n",
- block);
- result = 1;
- }
-
- result |= fp (0, NULL);
-
- foop = dlsym (h, "foo");
- if (foop == NULL)
- {
- printf ("cannot get symbol 'foo' the second time: %s\n", dlerror ());
- exit (1);
- }
- if (*foop != 16)
- {
- puts ("foo != 16");
- result = 1;
- }
-
- /* Now the module's TLS block has been used and should appear. */
- if (dlinfo (h, RTLD_DI_TLS_DATA, &block))
- {
- printf ("dlinfo RTLD_DI_TLS_DATA failed the second time: %s\n",
- dlerror ());
- result = 1;
- }
- else if (block != foop)
- {
- printf ("dlinfo RTLD_DI_TLS_DATA says %p but should be %p\n",
- block, foop);
- result = 1;
- }
-
- dlclose (h);
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls-manydynamic.c b/elf/tst-tls-manydynamic.c
deleted file mode 100644
index b072d0be68..0000000000
--- a/elf/tst-tls-manydynamic.c
+++ /dev/null
@@ -1,151 +0,0 @@
-/* Test with many dynamic TLS variables.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This test intends to exercise dynamic TLS variable allocation. It
- achieves this by combining dlopen (to avoid static TLS allocation
- after static TLS resizing), many DSOs with a large variable (to
- exceed the static TLS reserve), and an already-running thread (to
- force full dynamic TLS initialization). */
-
-#include "tst-tls-manydynamic.h"
-
-#include <errno.h>
-#include <dlfcn.h>
-#include <pthread.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-static int do_test (void);
-#include <support/xthread.h>
-#include <support/test-driver.c>
-
-void *handles[COUNT];
-set_value_func set_value_funcs[COUNT];
-get_value_func get_value_funcs[COUNT];
-
-static void
-init_functions (void)
-{
- for (int i = 0; i < COUNT; ++i)
- {
- /* Open the module. */
- {
- char soname[100];
- snprintf (soname, sizeof (soname), "tst-tls-manydynamic%02dmod.so", i);
- handles[i] = dlopen (soname, RTLD_LAZY);
- if (handles[i] == NULL)
- {
- printf ("error: dlopen failed: %s\n", dlerror ());
- exit (1);
- }
- }
-
- /* Obtain the setter function. */
- {
- char fname[100];
- snprintf (fname, sizeof (fname), "set_value_%02d", i);
- void *func = dlsym (handles[i], fname);
- if (func == NULL)
- {
- printf ("error: dlsym: %s\n", dlerror ());
- exit (1);
- }
- set_value_funcs[i] = func;
- }
-
- /* Obtain the getter function. */
- {
- char fname[100];
- snprintf (fname, sizeof (fname), "get_value_%02d", i);
- void *func = dlsym (handles[i], fname);
- if (func == NULL)
- {
- printf ("error: dlsym: %s\n", dlerror ());
- exit (1);
- }
- get_value_funcs[i] = func;
- }
- }
-}
-
-static pthread_barrier_t barrier;
-
-/* Running thread which forces real TLS initialization. */
-static void *
-blocked_thread_func (void *closure)
-{
- xpthread_barrier_wait (&barrier);
-
- /* TLS test runs here in the main thread. */
-
- xpthread_barrier_wait (&barrier);
- return NULL;
-}
-
-static int
-do_test (void)
-{
- {
- int ret = pthread_barrier_init (&barrier, NULL, 2);
- if (ret != 0)
- {
- errno = ret;
- printf ("error: pthread_barrier_init: %m\n");
- exit (1);
- }
- }
-
- pthread_t blocked_thread = xpthread_create (NULL, blocked_thread_func, NULL);
- xpthread_barrier_wait (&barrier);
-
- init_functions ();
-
- struct value values[COUNT];
- /* Initialze the TLS variables. */
- for (int i = 0; i < COUNT; ++i)
- {
- for (int j = 0; j < PER_VALUE_COUNT; ++j)
- values[i].num[j] = rand ();
- set_value_funcs[i] (&values[i]);
- }
-
- /* Read back their values to check that they do not overlap. */
- for (int i = 0; i < COUNT; ++i)
- {
- struct value actual;
- get_value_funcs[i] (&actual);
-
- for (int j = 0; j < PER_VALUE_COUNT; ++j)
- if (actual.num[j] != values[i].num[j])
- {
- printf ("error: mismatch at variable %d/%d: %d != %d\n",
- i, j, actual.num[j], values[i].num[j]);
- exit (1);
- }
- }
-
- xpthread_barrier_wait (&barrier);
- xpthread_join (blocked_thread);
-
- /* Close the modules. */
- for (int i = 0; i < COUNT; ++i)
- dlclose (handles[i]);
-
- return 0;
-}
diff --git a/elf/tst-tls-manydynamic.h b/elf/tst-tls-manydynamic.h
deleted file mode 100644
index 13fac4e7e8..0000000000
--- a/elf/tst-tls-manydynamic.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/* Interfaces for test with many dynamic TLS variables.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifndef TST_TLS_MANYDYNAMIC_H
-#define TST_TLS_MANYDYNAMIC_H
-
-enum
- {
- /* This many TLS variables (and modules) are defined. */
- COUNT = 100,
-
- /* Number of elements in the TLS variable. */
- PER_VALUE_COUNT = 1,
- };
-
-/* The TLS variables are of this type. We use a larger type to ensure
- that we can reach the static TLS limit with COUNT variables. */
-struct value
-{
- int num[PER_VALUE_COUNT];
-};
-
-/* Set the TLS variable defined in the module. */
-typedef void (*set_value_func) (const struct value *);
-
-/* Read the TLS variable defined in the module. */
-typedef void (*get_value_func) (struct value *);
-
-#endif /* TST_TLS_MANYDYNAMICMOD_H */
diff --git a/elf/tst-tls-manydynamicmod.c b/elf/tst-tls-manydynamicmod.c
deleted file mode 100644
index edfaeef7f3..0000000000
--- a/elf/tst-tls-manydynamicmod.c
+++ /dev/null
@@ -1,36 +0,0 @@
-/* Module for test with many dynamic TLS variables.
- Copyright (C) 2016-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file is parameterized by macros NAME, SETTER, GETTER, which
- are set form the Makefile. */
-
-#include "tst-tls-manydynamic.h"
-
-__thread struct value NAME;
-
-void
-SETTER (const struct value *value)
-{
- NAME = *value;
-}
-
-void
-GETTER (struct value *value)
-{
- *value = NAME;
-}
diff --git a/elf/tst-tls1-static.c b/elf/tst-tls1-static.c
deleted file mode 100644
index a01008073b..0000000000
--- a/elf/tst-tls1-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-tls1.c"
diff --git a/elf/tst-tls1.c b/elf/tst-tls1.c
deleted file mode 100644
index c31da56ce9..0000000000
--- a/elf/tst-tls1.c
+++ /dev/null
@@ -1,82 +0,0 @@
-/* glibc test for TLS in ld.so. */
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-/* Two common 'int' variables in TLS. */
-COMMON_INT_DEF(foo);
-COMMON_INT_DEF(bar);
-
-
-static int
-do_test (void)
-{
- int result = 0;
- int *ap, *bp;
-
-
- /* Set the variable using the local exec model. */
- puts ("set bar to 1 (LE)");
- ap = TLS_LE (bar);
- *ap = 1;
-
-
- /* Get variables using initial exec model. */
- fputs ("get sum of foo and bar (IE)", stdout);
- ap = TLS_IE (foo);
- bp = TLS_IE (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
-
- /* Get variables using local dynamic model. */
- fputs ("get sum of foo and bar (LD)", stdout);
- ap = TLS_LD (foo);
- bp = TLS_LD (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
-
- /* Get variables using generic dynamic model. */
- fputs ("get sum of foo and bar (GD)", stdout);
- ap = TLS_GD (foo);
- bp = TLS_GD (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls10.c b/elf/tst-tls10.c
deleted file mode 100644
index d9611aac6d..0000000000
--- a/elf/tst-tls10.c
+++ /dev/null
@@ -1,39 +0,0 @@
-#include "tst-tls10.h"
-
-__thread int dummy __attribute__((visibility ("hidden"))) = 12;
-__thread struct A local = { 1, 2, 3 };
-
-#define CHECK(N, S) \
- p = f##N##a (); \
- if (p->a != S || p->b != S + 1 || p->c != S + 2) \
- abort ()
-
-static int
-do_test (void)
-{
- struct A *p;
- if (local.a != 1 || local.b != 2 || local.c != 3)
- abort ();
- if (a1.a != 4 || a1.b != 5 || a1.c != 6)
- abort ();
- if (a2.a != 22 || a2.b != 23 || a2.c != 24)
- abort ();
- if (a3.a != 10 || a3.b != 11 || a3.c != 12)
- abort ();
- if (a4.a != 25 || a4.b != 26 || a4.c != 27)
- abort ();
- check1 ();
- check2 ();
- if (f1a () != &a1 || f2a () != &a2 || f3a () != &a3 || f4a () != &a4)
- abort ();
- CHECK (5, 16);
- CHECK (6, 19);
- if (f7a () != &a2 || f8a () != &a4)
- abort ();
- CHECK (9, 28);
- CHECK (10, 31);
-
- exit (0);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls10.h b/elf/tst-tls10.h
deleted file mode 100644
index 7c8c6a6391..0000000000
--- a/elf/tst-tls10.h
+++ /dev/null
@@ -1,32 +0,0 @@
-#include <stdlib.h>
-
-struct A
-{
- char a;
- int b;
- long long c;
-};
-
-extern __thread struct A a1, a2, a3, a4;
-extern struct A *f1a (void);
-extern struct A *f2a (void);
-extern struct A *f3a (void);
-extern struct A *f4a (void);
-extern struct A *f5a (void);
-extern struct A *f6a (void);
-extern struct A *f7a (void);
-extern struct A *f8a (void);
-extern struct A *f9a (void);
-extern struct A *f10a (void);
-extern int f1b (void);
-extern int f2b (void);
-extern int f3b (void);
-extern int f4b (void);
-extern int f5b (void);
-extern int f6b (void);
-extern int f7b (void);
-extern int f8b (void);
-extern int f9b (void);
-extern int f10b (void);
-extern void check1 (void);
-extern void check2 (void);
diff --git a/elf/tst-tls11.c b/elf/tst-tls11.c
deleted file mode 100644
index a5c3dd70b0..0000000000
--- a/elf/tst-tls11.c
+++ /dev/null
@@ -1,28 +0,0 @@
-#include "tst-tls10.h"
-
-#define CHECK(N, S) \
- p = f##N##a (); \
- if (p->a != S || p->b != S + 1 || p->c != S + 2) \
- abort ()
-
-static int
-do_test (void)
-{
- struct A *p;
- check1 ();
- check2 ();
- CHECK (1, 4);
- CHECK (2, 22);
- CHECK (3, 10);
- CHECK (4, 25);
- CHECK (5, 16);
- CHECK (6, 19);
- CHECK (7, 22);
- CHECK (8, 25);
- CHECK (9, 28);
- CHECK (10, 31);
-
- exit (0);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls12.c b/elf/tst-tls12.c
deleted file mode 100644
index ccd5f8b43e..0000000000
--- a/elf/tst-tls12.c
+++ /dev/null
@@ -1,19 +0,0 @@
-#include "tst-tls10.h"
-
-#define CHECK(N, S) \
- p = &a##N; \
- if (p->a != S || p->b != S + 1 || p->c != S + 2) \
- abort ()
-
-static int
-do_test (void)
-{
- struct A *p;
- check1 ();
- CHECK (1, 4);
- CHECK (2, 7);
-
- exit (0);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls13.c b/elf/tst-tls13.c
deleted file mode 100644
index b1d303310f..0000000000
--- a/elf/tst-tls13.c
+++ /dev/null
@@ -1,28 +0,0 @@
-/* Check unloading modules with data in static TLS block. */
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <unistd.h>
-
-
-static int
-do_test (void)
-{
- for (int i = 0; i < 1000;)
- {
- printf ("round %d\n",++i);
-
- void *h = dlopen ("$ORIGIN/tst-tlsmod13a.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot load: %s\n", dlerror ());
- exit (1);
- }
-
- dlclose (h);
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls14.c b/elf/tst-tls14.c
deleted file mode 100644
index a6a79ef24f..0000000000
--- a/elf/tst-tls14.c
+++ /dev/null
@@ -1,54 +0,0 @@
-/* Check alignment of TLS variable. */
-#include <dlfcn.h>
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#define AL 4096
-struct foo
-{
- int i;
-} __attribute ((aligned (AL)));
-
-static __thread struct foo f;
-static struct foo g;
-
-
-extern int in_dso1 (void);
-
-
-static int
-do_test (void)
-{
- int result = 0;
-
- int fail = (((uintptr_t) &f) & (AL - 1)) != 0;
- printf ("&f = %p %s\n", &f, fail ? "FAIL" : "OK");
- result |= fail;
-
- fail = (((uintptr_t) &g) & (AL - 1)) != 0;
- printf ("&g = %p %s\n", &g, fail ? "FAIL" : "OK");
- result |= fail;
-
- result |= in_dso1 ();
-
- void *h = dlopen ("tst-tlsmod14b.so", RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open tst-tlsmod14b.so: %m\n");
- exit (1);
- }
-
- int (*fp) (void) = (int (*) (void)) dlsym (h, "in_dso2");
- if (fp == NULL)
- {
- puts ("cannot find in_dso2");
- exit (1);
- }
-
- result |= fp ();
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls15.c b/elf/tst-tls15.c
deleted file mode 100644
index db2a4f4b77..0000000000
--- a/elf/tst-tls15.c
+++ /dev/null
@@ -1,32 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- void *h = dlopen ("tst-tlsmod15a.so", RTLD_NOW);
- if (h != NULL)
- {
- puts ("unexpectedly succeeded to open tst-tlsmod15a.so");
- exit (1);
- }
-
- h = dlopen ("tst-tlsmod15b.so", RTLD_NOW);
- if (h == NULL)
- {
- puts ("failed to open tst-tlsmod15b.so");
- exit (1);
- }
-
- int (*fp) (void) = (int (*) (void)) dlsym (h, "in_dso");
- if (fp == NULL)
- {
- puts ("cannot find in_dso");
- exit (1);
- }
-
- return fp ();
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls16.c b/elf/tst-tls16.c
deleted file mode 100644
index f2830b8a4f..0000000000
--- a/elf/tst-tls16.c
+++ /dev/null
@@ -1,52 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- void *h = dlopen ("tst-tlsmod16a.so", RTLD_LAZY | RTLD_GLOBAL);
- if (h == NULL)
- {
- puts ("unexpectedly failed to open tst-tlsmod16a.so");
- exit (1);
- }
-
- void *p = dlsym (h, "tlsvar");
-
- /* This dlopen should indeed fail, because tlsvar was assigned to
- dynamic TLS, and the new module requests it to be in static TLS.
- However, there's a possibility that dlopen succeeds if the
- variable is, for whatever reason, assigned to static TLS, or if
- the module fails to require static TLS, or even if TLS is not
- supported. */
- h = dlopen ("tst-tlsmod16b.so", RTLD_NOW | RTLD_GLOBAL);
- if (h == NULL)
- {
- return 0;
- }
-
- puts ("unexpectedly succeeded to open tst-tlsmod16b.so");
-
-
- void *(*fp) (void) = (void *(*) (void)) dlsym (h, "in_dso");
- if (fp == NULL)
- {
- puts ("cannot find in_dso");
- exit (1);
- }
-
- /* If the dlopen passes, at least make sure the address returned by
- dlsym is the same as that returned by the initial-exec access.
- If the variable was assigned to dynamic TLS during dlsym, this
- portion will fail. */
- if (fp () != p)
- {
- puts ("returned values do not match");
- exit (1);
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls17.c b/elf/tst-tls17.c
deleted file mode 100644
index c2a972d3c4..0000000000
--- a/elf/tst-tls17.c
+++ /dev/null
@@ -1,28 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- void *h = dlopen ("tst-tlsmod17b.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("unexpectedly failed to open tst-tlsmod17b.so");
- exit (1);
- }
-
- int (*fp) (void) = (int (*) (void)) dlsym (h, "tlsmod17b");
- if (fp == NULL)
- {
- puts ("cannot find tlsmod17b");
- exit (1);
- }
-
- if (fp ())
- exit (1);
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls18.c b/elf/tst-tls18.c
deleted file mode 100644
index b705b61d60..0000000000
--- a/elf/tst-tls18.c
+++ /dev/null
@@ -1,37 +0,0 @@
-#include <dlfcn.h>
-#include <stdlib.h>
-#include <stdio.h>
-
-static int
-do_test (void)
-{
- char modname[sizeof "tst-tlsmod18aXX.so"];
- void *h[20];
- for (int i = 0; i < 20; i++)
- {
- snprintf (modname, sizeof modname, "tst-tlsmod18a%d.so", i);
- h[i] = dlopen (modname, RTLD_LAZY);
- if (h[i] == NULL)
- {
- printf ("unexpectedly failed to open %s", modname);
- exit (1);
- }
- }
-
- for (int i = 0; i < 20; i++)
- {
- int (*fp) (void) = (int (*) (void)) dlsym (h[i], "test");
- if (fp == NULL)
- {
- printf ("cannot find test in tst-tlsmod18a%d.so", i);
- exit (1);
- }
-
- if (fp ())
- exit (1);
- }
-
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls19.c b/elf/tst-tls19.c
deleted file mode 100644
index dd8ea42c3f..0000000000
--- a/elf/tst-tls19.c
+++ /dev/null
@@ -1,26 +0,0 @@
-// BZ 12453
-#include <stdio.h>
-#include <dlfcn.h>
-
-
-static int
-do_test (void)
-{
- void* dl = dlopen ("tst-tls19mod1.so", RTLD_LAZY | RTLD_GLOBAL);
- if (dl == NULL)
- {
- printf ("Error loading tst-tls19mod1.so: %s\n", dlerror ());
- return 1;
- }
-
- int (*fn) (void) = dlsym (dl, "foo");
- if (fn == NULL)
- {
- printf("Error obtaining symbol foo\n");
- return 1;
- }
-
- return fn ();
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls19mod1.c b/elf/tst-tls19mod1.c
deleted file mode 100644
index 2790097ae5..0000000000
--- a/elf/tst-tls19mod1.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <stdio.h>
-
-extern int bar (void);
-extern int baz (void);
-
-int
-foo (void)
-{
- int v1 = bar ();
- int v2 = baz ();
-
- printf ("bar=%d, baz=%d\n", v1, v2);
-
- return v1 != 666 || v2 != 42;
-}
diff --git a/elf/tst-tls19mod2.c b/elf/tst-tls19mod2.c
deleted file mode 100644
index cae702f67c..0000000000
--- a/elf/tst-tls19mod2.c
+++ /dev/null
@@ -1,13 +0,0 @@
-static int __thread tbar __attribute__ ((tls_model ("initial-exec"))) = 666;
-
-void
-setter (int a)
-{
- tbar = a;
-}
-
-int
-bar (void)
-{
- return tbar;
-}
diff --git a/elf/tst-tls19mod3.c b/elf/tst-tls19mod3.c
deleted file mode 100644
index e7b28016b3..0000000000
--- a/elf/tst-tls19mod3.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-static int __thread tbaz __attribute__ ((tls_model ("local-dynamic"))) = 42;
-
-void
-setter2 (int a)
-{
- tbaz = a;
-}
-
-int
-baz (void)
-{
- printf ("&tbaz=%p\n", &tbaz);
- return tbaz;
-}
diff --git a/elf/tst-tls2-static.c b/elf/tst-tls2-static.c
deleted file mode 100644
index 55ffa57448..0000000000
--- a/elf/tst-tls2-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-tls2.c"
diff --git a/elf/tst-tls2.c b/elf/tst-tls2.c
deleted file mode 100644
index 963b8d6c88..0000000000
--- a/elf/tst-tls2.c
+++ /dev/null
@@ -1,82 +0,0 @@
-/* glibc test for TLS in ld.so. */
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-/* Two 'int' variables in TLS. */
-VAR_INT_DEF(foo);
-VAR_INT_DEF(bar);
-
-
-static int
-do_test (void)
-{
- int result = 0;
- int *ap, *bp;
-
-
- /* Set the variable using the local exec model. */
- puts ("set bar to 1 (LE)");
- ap = TLS_LE (bar);
- *ap = 1;
-
-
- /* Get variables using initial exec model. */
- fputs ("get sum of foo and bar (IE)", stdout);
- ap = TLS_IE (foo);
- bp = TLS_IE (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
-
- /* Get variables using local dynamic model. */
- fputs ("get sum of foo and bar (LD)", stdout);
- ap = TLS_LD (foo);
- bp = TLS_LD (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
-
- /* Get variables using generic dynamic model. */
- fputs ("get sum of foo and bar (GD)", stdout);
- ap = TLS_GD (foo);
- bp = TLS_GD (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 1;
- if (*ap != 0)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 1)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls3.c b/elf/tst-tls3.c
deleted file mode 100644
index 7e0abb4c58..0000000000
--- a/elf/tst-tls3.c
+++ /dev/null
@@ -1,67 +0,0 @@
-/* glibc test for TLS in ld.so. */
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-/* One define int variable, two externs. */
-COMMON_INT_DECL(foo);
-VAR_INT_DECL(bar);
-VAR_INT_DEF(baz);
-
-
-extern int in_dso (void);
-
-
-static int
-do_test (void)
-{
- int result = 0;
- int *ap, *bp, *cp;
-
-
- /* Set the variable using the local exec model. */
- puts ("set baz to 3 (LE)");
- ap = TLS_LE (baz);
- *ap = 3;
-
-
- /* Get variables using initial exec model. */
- puts ("set variables foo and bar (IE)");
- ap = TLS_IE (foo);
- *ap = 1;
- bp = TLS_IE (bar);
- *bp = 2;
-
-
- /* Get variables using local dynamic model. */
- fputs ("get sum of foo, bar (GD) and baz (LD)", stdout);
- ap = TLS_GD (foo);
- bp = TLS_GD (bar);
- cp = TLS_LD (baz);
- printf (" = %d\n", *ap + *bp + *cp);
- result |= *ap + *bp + *cp != 6;
- if (*ap != 1)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 2)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
- if (*cp != 3)
- {
- printf ("baz = %d\n", *cp);
- result = 1;
- }
-
-
- result |= in_dso ();
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls4.c b/elf/tst-tls4.c
deleted file mode 100644
index 6841f81386..0000000000
--- a/elf/tst-tls4.c
+++ /dev/null
@@ -1,49 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-tlsmod2.so";
- int result = 0;
- int *foop;
- int (*fp) (int, int *);
- void *h;
-
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- fp = dlsym (h, "in_dso");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso': %s\n", dlerror ());
- exit (1);
- }
-
- result |= fp (0, NULL);
-
- foop = dlsym (h, "foo");
- if (foop == NULL)
- {
- printf ("cannot get symbol 'foo' the second time: %s\n", dlerror ());
- exit (1);
- }
- if (*foop != 16)
- {
- puts ("foo != 16");
- result = 1;
- }
-
- dlclose (h);
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls5.c b/elf/tst-tls5.c
deleted file mode 100644
index 5f006fd645..0000000000
--- a/elf/tst-tls5.c
+++ /dev/null
@@ -1,65 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-tlsmod2.so";
- int result = 0;
- int *foop;
- int *foop2;
- int (*fp) (int, int *);
- void *h;
-
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- foop = dlsym (h, "foo");
- if (foop == NULL)
- {
- printf ("cannot get symbol 'foo': %s\n", dlerror ());
- exit (1);
- }
-
- *foop = 42;
-
- fp = dlsym (h, "in_dso");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso': %s\n", dlerror ());
- exit (1);
- }
-
- result |= fp (42, foop);
-
- foop2 = dlsym (h, "foo");
- if (foop2 == NULL)
- {
- printf ("cannot get symbol 'foo' the second time: %s\n", dlerror ());
- exit (1);
- }
-
- if (foop != foop2)
- {
- puts ("address of 'foo' different the second time");
- result = 1;
- }
- else if (*foop != 16)
- {
- puts ("foo != 16");
- result = 1;
- }
-
- dlclose (h);
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls6.c b/elf/tst-tls6.c
deleted file mode 100644
index df81c1f6b4..0000000000
--- a/elf/tst-tls6.c
+++ /dev/null
@@ -1,84 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <link.h>
-
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-tlsmod2.so";
- int result = 0;
- int *foop;
- int *foop2;
- int (*fp) (int, int *);
- void *h;
- int i;
- int modid = -1;
-
- for (i = 0; i < 10; ++i)
- {
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (modid == -1)
- modid = ((struct link_map *) h)->l_tls_modid;
- else if (((struct link_map *) h)->l_tls_modid != modid)
- {
- printf ("round %d: modid now %zd, initially %d\n",
- i, ((struct link_map *) h)->l_tls_modid, modid);
- result = 1;
- }
-
- foop = dlsym (h, "foo");
- if (foop == NULL)
- {
- printf ("cannot get symbol 'foo': %s\n", dlerror ());
- exit (1);
- }
-
- *foop = 42 + i;
-
- fp = dlsym (h, "in_dso");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso': %s\n", dlerror ());
- exit (1);
- }
-
- result |= fp (42 + i, foop);
-
- foop2 = dlsym (h, "foo");
- if (foop2 == NULL)
- {
- printf ("cannot get symbol 'foo' the second time: %s\n", dlerror ());
- exit (1);
- }
-
- if (foop != foop2)
- {
- puts ("address of 'foo' different the second time");
- result = 1;
- }
- else if (*foop != 16)
- {
- puts ("foo != 16");
- result = 1;
- }
-
- dlclose (h);
- }
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls7.c b/elf/tst-tls7.c
deleted file mode 100644
index fa46709600..0000000000
--- a/elf/tst-tls7.c
+++ /dev/null
@@ -1,55 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <link.h>
-
-
-static int
-do_test (void)
-{
- static const char modname[] = "tst-tlsmod3.so";
- int result = 0;
- int (*fp) (void);
- void *h;
- int i;
- int modid = -1;
-
- for (i = 0; i < 10; ++i)
- {
- h = dlopen (modname, RTLD_LAZY);
- if (h == NULL)
- {
- printf ("cannot open '%s': %s\n", modname, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (modid == -1)
- modid = ((struct link_map *) h)->l_tls_modid;
- else if (((struct link_map *) h)->l_tls_modid != (size_t) modid)
- {
- printf ("round %d: modid now %zu, initially %d\n",
- i, ((struct link_map *) h)->l_tls_modid, modid);
- result = 1;
- }
-
- fp = dlsym (h, "in_dso2");
- if (fp == NULL)
- {
- printf ("cannot get symbol 'in_dso2': %s\n", dlerror ());
- exit (1);
- }
-
- result |= fp ();
-
- dlclose (h);
- }
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls8.c b/elf/tst-tls8.c
deleted file mode 100644
index c779572617..0000000000
--- a/elf/tst-tls8.c
+++ /dev/null
@@ -1,167 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <link.h>
-
-
-static int
-do_test (void)
-{
- static const char modname1[] = "$ORIGIN/tst-tlsmod3.so";
- static const char modname2[] = "$ORIGIN/tst-tlsmod4.so";
- int result = 0;
- int (*fp1) (void);
- int (*fp2) (int, int *);
- void *h1;
- void *h2;
- int i;
- size_t modid1 = (size_t) -1;
- size_t modid2 = (size_t) -1;
- int *bazp;
-
- for (i = 0; i < 10; ++i)
- {
- h1 = dlopen (modname1, RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname1, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (modid1 == (size_t) -1)
- modid1 = ((struct link_map *) h1)->l_tls_modid;
- else if (((struct link_map *) h1)->l_tls_modid != modid1)
- {
- printf ("round %d: modid now %zd, initially %zd\n",
- i, ((struct link_map *) h1)->l_tls_modid, modid1);
- result = 1;
- }
-
- fp1 = dlsym (h1, "in_dso2");
- if (fp1 == NULL)
- {
- printf ("cannot get symbol 'in_dso2' in %s\n", modname1);
- exit (1);
- }
-
- result |= fp1 ();
-
-
-
- h2 = dlopen (modname2, RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname2, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (modid2 == (size_t) -1)
- modid2 = ((struct link_map *) h1)->l_tls_modid;
- else if (((struct link_map *) h1)->l_tls_modid != modid2)
- {
- printf ("round %d: modid now %zd, initially %zd\n",
- i, ((struct link_map *) h1)->l_tls_modid, modid2);
- result = 1;
- }
-
- bazp = dlsym (h2, "baz");
- if (bazp == NULL)
- {
- printf ("cannot get symbol 'baz' in %s\n", modname2);
- exit (1);
- }
-
- *bazp = 42 + i;
-
- fp2 = dlsym (h2, "in_dso");
- if (fp2 == NULL)
- {
- printf ("cannot get symbol 'in_dso' in %s\n", modname2);
- exit (1);
- }
-
- result |= fp2 (42 + i, bazp);
-
- dlclose (h1);
- dlclose (h2);
-
-
- h1 = dlopen (modname1, RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname1, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (((struct link_map *) h1)->l_tls_modid != modid1)
- {
- printf ("round %d: modid now %zd, initially %zd\n",
- i, ((struct link_map *) h1)->l_tls_modid, modid1);
- result = 1;
- }
-
- fp1 = dlsym (h1, "in_dso2");
- if (fp1 == NULL)
- {
- printf ("cannot get symbol 'in_dso2' in %s\n", modname1);
- exit (1);
- }
-
- result |= fp1 ();
-
-
-
- h2 = dlopen (modname2, RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname2, dlerror ());
- exit (1);
- }
-
- /* Dirty test code here: we peek into a private data structure.
- We make sure that the module gets assigned the same ID every
- time. The value of the first round is used. */
- if (((struct link_map *) h1)->l_tls_modid != modid2)
- {
- printf ("round %d: modid now %zd, initially %zd\n",
- i, ((struct link_map *) h1)->l_tls_modid, modid2);
- result = 1;
- }
-
- bazp = dlsym (h2, "baz");
- if (bazp == NULL)
- {
- printf ("cannot get symbol 'baz' in %s\n", modname2);
- exit (1);
- }
-
- *bazp = 62 + i;
-
- fp2 = dlsym (h2, "in_dso");
- if (fp2 == NULL)
- {
- printf ("cannot get symbol 'in_dso' in %s\n", modname2);
- exit (1);
- }
-
- result |= fp2 (62 + i, bazp);
-
- /* This time the dlclose calls are in reverse order. */
- dlclose (h2);
- dlclose (h1);
- }
-
- return result;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tls9-static.c b/elf/tst-tls9-static.c
deleted file mode 100644
index 51812ccc7d..0000000000
--- a/elf/tst-tls9-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-tls9.c"
diff --git a/elf/tst-tls9.c b/elf/tst-tls9.c
deleted file mode 100644
index ee21b47c70..0000000000
--- a/elf/tst-tls9.c
+++ /dev/null
@@ -1,36 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <link.h>
-
-static int
-do_test (void)
-{
- static const char modname1[] = "tst-tlsmod5.so";
- static const char modname2[] = "tst-tlsmod6.so";
- int result = 0;
-
- void *h1 = dlopen (modname1, RTLD_LAZY);
- if (h1 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname1, dlerror ());
- result = 1;
- }
- void *h2 = dlopen (modname2, RTLD_LAZY);
- if (h2 == NULL)
- {
- printf ("cannot open '%s': %s\n", modname2, dlerror ());
- result = 1;
- }
-
- if (h1 != NULL)
- dlclose (h1);
- if (h2 != NULL)
- dlclose (h2);
-
- return result;
-}
-
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tlsalign-extern-static.c b/elf/tst-tlsalign-extern-static.c
deleted file mode 100644
index e84900eee4..0000000000
--- a/elf/tst-tlsalign-extern-static.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-tlsalign-extern.c"
diff --git a/elf/tst-tlsalign-extern.c b/elf/tst-tlsalign-extern.c
deleted file mode 100644
index 11384d085e..0000000000
--- a/elf/tst-tlsalign-extern.c
+++ /dev/null
@@ -1,73 +0,0 @@
-/* Test for large alignment in TLS blocks (extern case), BZ#18383.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-/* This is the same as tst-tlsalign-static.c, except that it uses
- TLS variables that are defined in a separate translation unit
- (ts-tlsalign-vars.c). It turned out that the cause of BZ#18383
- on ARM was actually an ARM assembler bug triggered by the ways of
- using .tdata/.tbss sections and relocs referring to them that GCC
- chooses when the variables are defined in the same translation
- unit that contains the references. */
-
-extern __thread int tdata1;
-extern __thread int tdata2;
-extern __thread int tdata3;
-extern __thread int tbss1;
-extern __thread int tbss2;
-extern __thread int tbss3;
-
-static int
-test_one (const char *which, unsigned int alignment, int *var, int value)
-{
- uintptr_t addr = (uintptr_t) var;
- unsigned int misalign = addr & (alignment - 1);
-
- printf ("%s TLS address %p %% %u = %u\n",
- which, (void *) var, alignment, misalign);
-
- int got = *var;
- if (got != value)
- {
- printf ("%s value %d should be %d\n", which, got, value);
- return 1;
- }
-
- return misalign != 0;
-}
-
-static int
-do_test (void)
-{
- int fail = 0;
-
- fail |= test_one ("tdata1", 4, &tdata1, 1);
- fail |= test_one ("tdata2", 0x10, &tdata2, 2);
- fail |= test_one ("tdata3", 0x1000, &tdata3, 4);
-
- fail |= test_one ("tbss1", 4, &tbss1, 0);
- fail |= test_one ("tbss2", 0x10, &tbss2, 0);
- fail |= test_one ("tbss3", 0x1000, &tbss3, 0);
-
- return fail ? EXIT_FAILURE : EXIT_SUCCESS;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tlsalign-lib.c b/elf/tst-tlsalign-lib.c
deleted file mode 100644
index 4371e581a6..0000000000
--- a/elf/tst-tlsalign-lib.c
+++ /dev/null
@@ -1,6 +0,0 @@
-__thread int mod_tdata1 = 1;
-__thread int mod_tdata2 __attribute__ ((aligned (0x10))) = 2;
-__thread int mod_tdata3 __attribute__ ((aligned (0x1000))) = 4;
-__thread int mod_tbss1;
-__thread int mod_tbss2 __attribute__ ((aligned (0x10)));
-__thread int mod_tbss3 __attribute__ ((aligned (0x1000)));
diff --git a/elf/tst-tlsalign-static.c b/elf/tst-tlsalign-static.c
deleted file mode 100644
index 1671abf28e..0000000000
--- a/elf/tst-tlsalign-static.c
+++ /dev/null
@@ -1,2 +0,0 @@
-#define NO_LIB
-#include "tst-tlsalign.c"
diff --git a/elf/tst-tlsalign-vars.c b/elf/tst-tlsalign-vars.c
deleted file mode 100644
index 01b3501d3b..0000000000
--- a/elf/tst-tlsalign-vars.c
+++ /dev/null
@@ -1,28 +0,0 @@
-/* This is for tst-tlsalign-extern.c, which see. It's essential for the
- purpose of the test that these definitions be in a separate translation
- unit from the code using the variables. */
-
-__thread int tdata1 = 1;
-__thread int tdata2 __attribute__ ((aligned (0x10))) = 2;
-__thread int tdata3 __attribute__ ((aligned (0x1000))) = 4;
-__thread int tbss1;
-__thread int tbss2 __attribute__ ((aligned (0x10)));
-__thread int tbss3 __attribute__ ((aligned (0x1000)));
-
-/* This function is never called. But its presence in this translation
- unit makes GCC emit the variables above in the order defined (perhaps
- because it's the order in which they're used here?) rather than
- reordering them into descending order of alignment requirement--and so
- keeps it more similar to the tst-tlsalign-static.c case--just in case
- that affects the bug (though there is no evidence that it does). */
-
-void
-unused (void)
-{
- tdata1 = -1;
- tdata2 = -2;
- tdata3 = -3;
- tbss1 = -4;
- tbss2 = -5;
- tbss3 = -6;
-}
diff --git a/elf/tst-tlsalign.c b/elf/tst-tlsalign.c
deleted file mode 100644
index b129ebda0e..0000000000
--- a/elf/tst-tlsalign.c
+++ /dev/null
@@ -1,84 +0,0 @@
-/* Test for large alignment in TLS blocks, BZ#18383.
- Copyright (C) 2015-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-static __thread int tdata1 = 1;
-static __thread int tdata2 __attribute__ ((aligned (0x10))) = 2;
-static __thread int tdata3 __attribute__ ((aligned (0x1000))) = 4;
-static __thread int tbss1;
-static __thread int tbss2 __attribute__ ((aligned (0x10)));
-static __thread int tbss3 __attribute__ ((aligned (0x1000)));
-
-#ifndef NO_LIB
-extern __thread int mod_tdata1;
-extern __thread int mod_tdata2;
-extern __thread int mod_tdata3;
-extern __thread int mod_tbss1;
-extern __thread int mod_tbss2;
-extern __thread int mod_tbss3;
-#endif
-
-static int
-test_one (const char *which, unsigned int alignment, int *var, int value)
-{
- uintptr_t addr = (uintptr_t) var;
- unsigned int misalign = addr & (alignment - 1);
-
- printf ("%s TLS address %p %% %u = %u\n",
- which, (void *) var, alignment, misalign);
-
- int got = *var;
- if (got != value)
- {
- printf ("%s value %d should be %d\n", which, got, value);
- return 1;
- }
-
- return misalign != 0;
-}
-
-static int
-do_test (void)
-{
- int fail = 0;
-
- fail |= test_one ("tdata1", 4, &tdata1, 1);
- fail |= test_one ("tdata2", 0x10, &tdata2, 2);
- fail |= test_one ("tdata3", 0x1000, &tdata3, 4);
-
- fail |= test_one ("tbss1", 4, &tbss1, 0);
- fail |= test_one ("tbss2", 0x10, &tbss2, 0);
- fail |= test_one ("tbss3", 0x1000, &tbss3, 0);
-
-#ifndef NO_LIB
- fail |= test_one ("mod_tdata1", 4, &mod_tdata1, 1);
- fail |= test_one ("mod_tdata2", 0x10, &mod_tdata2, 2);
- fail |= test_one ("mod_tdata3", 0x1000, &mod_tdata3, 4);
-
- fail |= test_one ("mod_tbss1", 4, &mod_tbss1, 0);
- fail |= test_one ("mod_tbss2", 0x10, &mod_tbss2, 0);
- fail |= test_one ("mod_tbss3", 0x1000, &mod_tbss3, 0);
-#endif
-
- return fail ? EXIT_FAILURE : EXIT_SUCCESS;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-tlsmod1.c b/elf/tst-tlsmod1.c
deleted file mode 100644
index 8d9156791b..0000000000
--- a/elf/tst-tlsmod1.c
+++ /dev/null
@@ -1,62 +0,0 @@
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-/* One define int variable, two externs. */
-COMMON_INT_DEF(foo);
-VAR_INT_DEF(bar);
-VAR_INT_DECL(baz);
-
-extern int in_dso (void);
-
-int
-in_dso (void)
-{
- int result = 0;
- int *ap, *bp, *cp;
-
- /* Get variables using initial exec model. */
- fputs ("get sum of foo and bar (IE)", stdout);
- asm ("" ::: "memory");
- ap = TLS_IE (foo);
- bp = TLS_IE (bar);
- printf (" = %d\n", *ap + *bp);
- result |= *ap + *bp != 3;
- if (*ap != 1)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 2)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
-
-
- /* Get variables using generic dynamic model. */
- fputs ("get sum of foo and bar and baz (GD)", stdout);
- ap = TLS_GD (foo);
- bp = TLS_GD (bar);
- cp = TLS_GD (baz);
- printf (" = %d\n", *ap + *bp + *cp);
- result |= *ap + *bp + *cp != 6;
- if (*ap != 1)
- {
- printf ("foo = %d\n", *ap);
- result = 1;
- }
- if (*bp != 2)
- {
- printf ("bar = %d\n", *bp);
- result = 1;
- }
- if (*cp != 3)
- {
- printf ("baz = %d\n", *cp);
- result = 1;
- }
-
- return result;
-}
diff --git a/elf/tst-tlsmod10.c b/elf/tst-tlsmod10.c
deleted file mode 100644
index 32e54f3c04..0000000000
--- a/elf/tst-tlsmod10.c
+++ /dev/null
@@ -1 +0,0 @@
-#include "tst-tlsmod8.c"
diff --git a/elf/tst-tlsmod11.c b/elf/tst-tlsmod11.c
deleted file mode 100644
index cffbd68edc..0000000000
--- a/elf/tst-tlsmod11.c
+++ /dev/null
@@ -1,4 +0,0 @@
-#include "tst-tls10.h"
-
-__thread struct A a1 = { 4, 5, 6 };
-__thread struct A a2 = { 7, 8, 9 };
diff --git a/elf/tst-tlsmod12.c b/elf/tst-tlsmod12.c
deleted file mode 100644
index d0be51891a..0000000000
--- a/elf/tst-tlsmod12.c
+++ /dev/null
@@ -1,12 +0,0 @@
-#include "tst-tls10.h"
-
-extern __thread struct A a2 __attribute__((tls_model("initial-exec")));
-
-void
-check1 (void)
-{
- if (a1.a != 4 || a1.b != 5 || a1.c != 6)
- abort ();
- if (a2.a != 7 || a2.b != 8 || a2.c != 9)
- abort ();
-}
diff --git a/elf/tst-tlsmod13.c b/elf/tst-tlsmod13.c
deleted file mode 100644
index 7712d8b8c8..0000000000
--- a/elf/tst-tlsmod13.c
+++ /dev/null
@@ -1,7 +0,0 @@
-__thread int a[2] __attribute__ ((tls_model ("initial-exec")));
-
-int
-foo (void)
-{
- return a[0];
-}
diff --git a/elf/tst-tlsmod13a.c b/elf/tst-tlsmod13a.c
deleted file mode 100644
index ca4eaccbff..0000000000
--- a/elf/tst-tlsmod13a.c
+++ /dev/null
@@ -1,9 +0,0 @@
-__thread int b[2] __attribute__ ((tls_model ("initial-exec")));
-
-extern int foo (void);
-
-int
-bar (void)
-{
- return foo () + b[0];
-}
diff --git a/elf/tst-tlsmod14a.c b/elf/tst-tlsmod14a.c
deleted file mode 100644
index 824c06d1f9..0000000000
--- a/elf/tst-tlsmod14a.c
+++ /dev/null
@@ -1,35 +0,0 @@
-#include <stdint.h>
-#include <stdio.h>
-
-#define AL 4096
-struct foo
-{
- int i;
-} __attribute ((aligned (AL)));
-
-static __thread struct foo f;
-static struct foo g;
-
-
-#ifndef FCT
-# define FCT in_dso1
-#endif
-
-
-int
-FCT (void)
-{
- puts (__func__);
-
- int result = 0;
-
- int fail = (((uintptr_t) &f) & (AL - 1)) != 0;
- printf ("&f = %p %s\n", &f, fail ? "FAIL" : "OK");
- result |= fail;
-
- fail = (((uintptr_t) &g) & (AL - 1)) != 0;
- printf ("&g = %p %s\n", &g, fail ? "FAIL" : "OK");
- result |= fail;
-
- return result;
-}
diff --git a/elf/tst-tlsmod14b.c b/elf/tst-tlsmod14b.c
deleted file mode 100644
index 24d9ceaf7e..0000000000
--- a/elf/tst-tlsmod14b.c
+++ /dev/null
@@ -1,2 +0,0 @@
-#define FCT in_dso2
-#include "tst-tlsmod14a.c"
diff --git a/elf/tst-tlsmod15a.c b/elf/tst-tlsmod15a.c
deleted file mode 100644
index 66c707129a..0000000000
--- a/elf/tst-tlsmod15a.c
+++ /dev/null
@@ -1,6 +0,0 @@
-extern int nonexistent_dummy_var;
-int *
-foo (void)
-{
- return &nonexistent_dummy_var;
-}
diff --git a/elf/tst-tlsmod15b.c b/elf/tst-tlsmod15b.c
deleted file mode 100644
index b37283686a..0000000000
--- a/elf/tst-tlsmod15b.c
+++ /dev/null
@@ -1,9 +0,0 @@
-#include "tst-tls10.h"
-
-__thread int mod15b_var __attribute__((tls_model("initial-exec")));
-
-int
-in_dso (void)
-{
- return mod15b_var;
-}
diff --git a/elf/tst-tlsmod16a.c b/elf/tst-tlsmod16a.c
deleted file mode 100644
index 4ec6a6c37d..0000000000
--- a/elf/tst-tlsmod16a.c
+++ /dev/null
@@ -1 +0,0 @@
-int __thread tlsvar;
diff --git a/elf/tst-tlsmod16b.c b/elf/tst-tlsmod16b.c
deleted file mode 100644
index 1ecba26dbe..0000000000
--- a/elf/tst-tlsmod16b.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern __thread int tlsvar __attribute__((tls_model("initial-exec")));
-
-void *
-in_dso (void)
-{
- return &tlsvar;
-}
diff --git a/elf/tst-tlsmod17a.c b/elf/tst-tlsmod17a.c
deleted file mode 100644
index 24c84a1590..0000000000
--- a/elf/tst-tlsmod17a.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <stdio.h>
-
-#ifndef N
-#define N 0
-#endif
-#define CONCAT1(s, n) s##n
-#define CONCAT(s, n) CONCAT1(s, n)
-
-__thread int CONCAT (v, N) = 4;
-
-int
-CONCAT (tlsmod17a, N) (void)
-{
- int *p = &CONCAT (v, N);
- /* GCC assumes &var is never NULL, add optimization barrier. */
- asm volatile ("" : "+r" (p));
- if (p == NULL || *p != 4)
- {
- printf ("fail %d %p\n", N, p);
- return 1;
- }
- return 0;
-}
diff --git a/elf/tst-tlsmod17b.c b/elf/tst-tlsmod17b.c
deleted file mode 100644
index 6178828737..0000000000
--- a/elf/tst-tlsmod17b.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#define P(N) extern int tlsmod17a##N (void);
-#define PS P(0) P(1) P(2) P(3) P(4) P(5) P(6) P(7) P(8) P(9) \
- P(10) P(12) P(13) P(14) P(15) P(16) P(17) P(18) P(19)
-PS
-#undef P
-
-int
-tlsmod17b (void)
-{
- int res = 0;
-#define P(N) res |= tlsmod17a##N ();
- PS
-#undef P
- return res;
-}
diff --git a/elf/tst-tlsmod18a.c b/elf/tst-tlsmod18a.c
deleted file mode 100644
index 1d728daa05..0000000000
--- a/elf/tst-tlsmod18a.c
+++ /dev/null
@@ -1,21 +0,0 @@
-#include <stdio.h>
-
-#ifndef N
-# define N 0
-#endif
-
-static __thread int var = 4;
-
-int
-test (void)
-{
- int *p = &var;
- /* GCC assumes &var is never NULL, add optimization barrier. */
- asm volatile ("" : "+r" (p));
- if (p == NULL || *p != 4)
- {
- printf ("fail %d %p\n", N, p);
- return 1;
- }
- return 0;
-}
diff --git a/elf/tst-tlsmod2.c b/elf/tst-tlsmod2.c
deleted file mode 100644
index 40eb1407f8..0000000000
--- a/elf/tst-tlsmod2.c
+++ /dev/null
@@ -1,34 +0,0 @@
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-COMMON_INT_DEF(foo);
-
-
-int
-in_dso (int n, int *caller_foop)
-{
- int *foop;
- int result = 0;
-
- puts ("foo"); /* Make sure PLT is used before macros. */
- asm ("" ::: "memory");
-
- foop = TLS_GD (foo);
-
- if (caller_foop != NULL && foop != caller_foop)
- {
- printf ("callers address of foo differs: %p vs %p\n", caller_foop, foop);
- result = 1;
- }
- else if (*foop != n)
- {
- printf ("foo != %d\n", n);
- result = 1;
- }
-
- *foop = 16;
-
- return result;
-}
diff --git a/elf/tst-tlsmod3.c b/elf/tst-tlsmod3.c
deleted file mode 100644
index 6d186c47ee..0000000000
--- a/elf/tst-tlsmod3.c
+++ /dev/null
@@ -1,37 +0,0 @@
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-extern int in_dso (int n, int *caller_foop);
-
-COMMON_INT_DEF(comm_n);
-
-
-
-
-int
-in_dso2 (void)
-{
- int *foop;
- int result = 0;
- static int n;
- int *np;
-
- puts ("foo"); /* Make sure PLT is used before macros. */
- asm ("" ::: "memory");
-
- foop = TLS_GD (foo);
- np = TLS_GD (comm_n);
-
- if (n != *np)
- {
- printf ("n = %d != comm_n = %d\n", n, *np);
- result = 1;
- }
-
- result |= in_dso (*foop = 42 + n++, foop);
-
- *foop = 16;
-
- return result;
-}
diff --git a/elf/tst-tlsmod4.c b/elf/tst-tlsmod4.c
deleted file mode 100644
index 86889aac7e..0000000000
--- a/elf/tst-tlsmod4.c
+++ /dev/null
@@ -1,34 +0,0 @@
-#include <stdio.h>
-
-#include "tls-macros.h"
-
-
-COMMON_INT_DEF(baz);
-
-
-int
-in_dso (int n, int *caller_bazp)
-{
- int *bazp;
- int result = 0;
-
- puts ("foo"); /* Make sure PLT is used before macros. */
- asm ("" ::: "memory");
-
- bazp = TLS_GD (baz);
-
- if (caller_bazp != NULL && bazp != caller_bazp)
- {
- printf ("callers address of baz differs: %p vs %p\n", caller_bazp, bazp);
- result = 1;
- }
- else if (*bazp != n)
- {
- printf ("baz != %d\n", n);
- result = 1;
- }
-
- *bazp = 16;
-
- return result;
-}
diff --git a/elf/tst-tlsmod5.c b/elf/tst-tlsmod5.c
deleted file mode 100644
index a97c7e5e0c..0000000000
--- a/elf/tst-tlsmod5.c
+++ /dev/null
@@ -1,3 +0,0 @@
-#include "tls-macros.h"
-
-COMMON_INT_DEF(foo);
diff --git a/elf/tst-tlsmod6.c b/elf/tst-tlsmod6.c
deleted file mode 100644
index e968596dd4..0000000000
--- a/elf/tst-tlsmod6.c
+++ /dev/null
@@ -1,3 +0,0 @@
-#include "tls-macros.h"
-
-COMMON_INT_DEF(bar);
diff --git a/elf/tst-tlsmod7.c b/elf/tst-tlsmod7.c
deleted file mode 100644
index 3df7907bcf..0000000000
--- a/elf/tst-tlsmod7.c
+++ /dev/null
@@ -1,101 +0,0 @@
-#include "tst-tls10.h"
-
-__thread int dummy __attribute__((visibility ("hidden"))) = 12;
-__thread struct A a1 = { 4, 5, 6 };
-__thread struct A a2 = { 7, 8, 9 };
-__thread struct A a3 __attribute__((tls_model("initial-exec")))
- = { 10, 11, 12 };
-__thread struct A a4 __attribute__((tls_model("initial-exec")))
- = { 13, 14, 15 };
-static __thread struct A local1 = { 16, 17, 18 };
-static __thread struct A local2 __attribute__((tls_model("initial-exec")))
- = { 19, 20, 21 };
-
-void
-check1 (void)
-{
- if (a1.a != 4 || a1.b != 5 || a1.c != 6)
- abort ();
- if (a2.a != 22 || a2.b != 23 || a2.c != 24)
- abort ();
- if (a3.a != 10 || a3.b != 11 || a3.c != 12)
- abort ();
- if (a4.a != 25 || a4.b != 26 || a4.c != 27)
- abort ();
- if (local1.a != 16 || local1.b != 17 || local1.c != 18)
- abort ();
- if (local2.a != 19 || local2.b != 20 || local2.c != 21)
- abort ();
-}
-
-struct A *
-f1a (void)
-{
- return &a1;
-}
-
-struct A *
-f2a (void)
-{
- return &a2;
-}
-
-struct A *
-f3a (void)
-{
- return &a3;
-}
-
-struct A *
-f4a (void)
-{
- return &a4;
-}
-
-struct A *
-f5a (void)
-{
- return &local1;
-}
-
-struct A *
-f6a (void)
-{
- return &local2;
-}
-
-int
-f1b (void)
-{
- return a1.a;
-}
-
-int
-f2b (void)
-{
- return a2.b;
-}
-
-int
-f3b (void)
-{
- return a3.c;
-}
-
-int
-f4b (void)
-{
- return a4.a;
-}
-
-int
-f5b (void)
-{
- return local1.b;
-}
-
-int
-f6b (void)
-{
- return local2.c;
-}
diff --git a/elf/tst-tlsmod8.c b/elf/tst-tlsmod8.c
deleted file mode 100644
index 89772ac42f..0000000000
--- a/elf/tst-tlsmod8.c
+++ /dev/null
@@ -1,70 +0,0 @@
-#include "tst-tls10.h"
-
-__thread long long dummy __attribute__((visibility ("hidden"))) = 12;
-__thread struct A a2 = { 22, 23, 24 };
-__thread struct A a4 __attribute__((tls_model("initial-exec")))
- = { 25, 26, 27 };
-static __thread struct A local1 = { 28, 29, 30 };
-static __thread struct A local2 __attribute__((tls_model("initial-exec")))
- = { 31, 32, 33 };
-
-void
-check2 (void)
-{
- if (a2.a != 22 || a2.b != 23 || a2.c != 24)
- abort ();
- if (a4.a != 25 || a4.b != 26 || a4.c != 27)
- abort ();
- if (local1.a != 28 || local1.b != 29 || local1.c != 30)
- abort ();
- if (local2.a != 31 || local2.b != 32 || local2.c != 33)
- abort ();
-}
-
-struct A *
-f7a (void)
-{
- return &a2;
-}
-
-struct A *
-f8a (void)
-{
- return &a4;
-}
-
-struct A *
-f9a (void)
-{
- return &local1;
-}
-
-struct A *
-f10a (void)
-{
- return &local2;
-}
-
-int
-f7b (void)
-{
- return a2.b;
-}
-
-int
-f8b (void)
-{
- return a4.a;
-}
-
-int
-f9b (void)
-{
- return local1.b;
-}
-
-int
-f10b (void)
-{
- return local2.c;
-}
diff --git a/elf/tst-tlsmod9.c b/elf/tst-tlsmod9.c
deleted file mode 100644
index 6b11ed58b8..0000000000
--- a/elf/tst-tlsmod9.c
+++ /dev/null
@@ -1,99 +0,0 @@
-#include "tst-tls10.h"
-
-__thread int dummy __attribute__((visibility ("hidden"))) = 12;
-__thread struct A a1 = { 4, 5, 6 };
-__thread struct A a3 __attribute__((tls_model("initial-exec")))
- = { 10, 11, 12 };
-extern __thread struct A a4 __attribute__((tls_model("initial-exec")));
-static __thread struct A local1 = { 16, 17, 18 };
-static __thread struct A local2 __attribute__((tls_model("initial-exec")))
- = { 19, 20, 21 };
-
-void
-check1 (void)
-{
- if (a1.a != 4 || a1.b != 5 || a1.c != 6)
- abort ();
- if (a2.a != 22 || a2.b != 23 || a2.c != 24)
- abort ();
- if (a3.a != 10 || a3.b != 11 || a3.c != 12)
- abort ();
- if (a4.a != 25 || a4.b != 26 || a4.c != 27)
- abort ();
- if (local1.a != 16 || local1.b != 17 || local1.c != 18)
- abort ();
- if (local2.a != 19 || local2.b != 20 || local2.c != 21)
- abort ();
-}
-
-struct A *
-f1a (void)
-{
- return &a1;
-}
-
-struct A *
-f2a (void)
-{
- return &a2;
-}
-
-struct A *
-f3a (void)
-{
- return &a3;
-}
-
-struct A *
-f4a (void)
-{
- return &a4;
-}
-
-struct A *
-f5a (void)
-{
- return &local1;
-}
-
-struct A *
-f6a (void)
-{
- return &local2;
-}
-
-int
-f1b (void)
-{
- return a1.a;
-}
-
-int
-f2b (void)
-{
- return a2.b;
-}
-
-int
-f3b (void)
-{
- return a3.c;
-}
-
-int
-f4b (void)
-{
- return a4.a;
-}
-
-int
-f5b (void)
-{
- return local1.b;
-}
-
-int
-f6b (void)
-{
- return local2.c;
-}
diff --git a/elf/tst-unique1.c b/elf/tst-unique1.c
deleted file mode 100644
index b5e53e49a0..0000000000
--- a/elf/tst-unique1.c
+++ /dev/null
@@ -1,73 +0,0 @@
-#include <config.h>
-#include <dlfcn.h>
-#include <stdio.h>
-#include <sys/mman.h>
-
-static int
-do_test (void)
-{
- void *h1 = dlopen ("tst-unique1mod1.so", RTLD_LAZY);
- if (h1 == NULL)
- {
- puts ("cannot load tst-unique1mod1");
- return 1;
- }
- int *(*f1) (void) = dlsym (h1, "f");
- if (f1 == NULL)
- {
- puts ("cannot locate f in tst-unique1mod1");
- return 1;
- }
- void *h2 = dlopen ("tst-unique1mod2.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("cannot load tst-unique1mod2");
- return 1;
- }
- int (*f2) (int *) = dlsym (h2, "f");
- if (f2 == NULL)
- {
- puts ("cannot locate f in tst-unique1mod2");
- return 1;
- }
- if (f2 (f1 ()))
- {
- puts ("f from tst-unique1mod2 failed");
- return 1;
- }
- dlclose (h2);
- dlclose (h1);
- mmap (NULL, 1024 * 1024 * 16, PROT_NONE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
- h2 = dlopen ("tst-unique1mod2.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("cannot load tst-unique1mod2");
- return 1;
- }
- f2 = dlsym (h2, "f");
- if (f2 == NULL)
- {
- puts ("cannot locate f in tst-unique1mod2");
- return 1;
- }
- h1 = dlopen ("tst-unique1mod1.so", RTLD_LAZY);
- if (h1 == NULL)
- {
- puts ("cannot load tst-unique1mod1");
- return 1;
- }
- f1 = dlsym (h1, "f");
- if (f1 == NULL)
- {
- puts ("cannot locate f in tst-unique1mod1");
- return 1;
- }
- if (f2 (f1 ()))
- {
- puts ("f from tst-unique1mod2 failed");
- return 1;
- }
- return 0;
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-unique1mod1.c b/elf/tst-unique1mod1.c
deleted file mode 100644
index 84b1f908d6..0000000000
--- a/elf/tst-unique1mod1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <config.h>
-
-asm (".data;"
- ".globl var\n"
- ".type var, %gnu_unique_object\n"
- ".size var, 4\n"
- "var:.zero 4\n"
- ".previous");
-extern int var;
-
-int *
-f (void)
-{
- var = 1;
- return &var;
-}
diff --git a/elf/tst-unique1mod2.c b/elf/tst-unique1mod2.c
deleted file mode 100644
index 126ca1ac6c..0000000000
--- a/elf/tst-unique1mod2.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <config.h>
-
-asm (".data;"
- ".globl var\n"
- ".type var, %gnu_unique_object\n"
- ".size var, 4\n"
- "var:.zero 4\n"
- ".previous");
-extern int var;
-
-int
-f (int *p)
-{
- return &var != p || *p != 1;
-}
diff --git a/elf/tst-unique2.c b/elf/tst-unique2.c
deleted file mode 100644
index e0173b7bcc..0000000000
--- a/elf/tst-unique2.c
+++ /dev/null
@@ -1,27 +0,0 @@
-#include <config.h>
-#include <dlfcn.h>
-#include <stdio.h>
-
-extern int var;
-
-static int
-do_test (void)
-{
- var = 1;
-
- void *h = dlopen ("tst-unique2mod2.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("cannot load tst-unique2mod2");
- return 1;
- }
- int (*f) (int *) = dlsym (h, "f");
- if (f == NULL)
- {
- puts ("cannot locate f in tst-unique2mod2");
- return 1;
- }
- return f (&var);
-}
-
-#include <support/test-driver.c>
diff --git a/elf/tst-unique2mod1.c b/elf/tst-unique2mod1.c
deleted file mode 100644
index 7cdb0eb0a0..0000000000
--- a/elf/tst-unique2mod1.c
+++ /dev/null
@@ -1,8 +0,0 @@
-#include <config.h>
-
-asm (".data;"
- ".globl var\n"
- ".type var, %gnu_unique_object\n"
- ".size var, 4\n"
- "var:.zero 4\n"
- ".previous");
diff --git a/elf/tst-unique2mod2.c b/elf/tst-unique2mod2.c
deleted file mode 100644
index 126ca1ac6c..0000000000
--- a/elf/tst-unique2mod2.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include <config.h>
-
-asm (".data;"
- ".globl var\n"
- ".type var, %gnu_unique_object\n"
- ".size var, 4\n"
- "var:.zero 4\n"
- ".previous");
-extern int var;
-
-int
-f (int *p)
-{
- return &var != p || *p != 1;
-}
diff --git a/elf/tst-unique3.cc b/elf/tst-unique3.cc
deleted file mode 100644
index efdd6d78c2..0000000000
--- a/elf/tst-unique3.cc
+++ /dev/null
@@ -1,24 +0,0 @@
-#include "tst-unique3.h"
-
-#include <cstdio>
-#include "../dlfcn/dlfcn.h"
-
-int t = S<char>::i;
-
-int
-main (void)
-{
- std::printf ("%d %d\n", S<char>::i, t);
- int result = S<char>::i++ != 1 || t != 1;
- result |= in_lib ();
- void *d = dlopen ("$ORIGIN/tst-unique3lib2.so", RTLD_LAZY);
- int (*fp) ();
- if (d == NULL || (fp = (int(*)()) dlsym (d, "in_lib2")) == NULL)
- {
- std::printf ("failed to get symbol in_lib2\n");
- return 1;
- }
- result |= fp ();
- dlclose (d);
- return result;
-}
diff --git a/elf/tst-unique3.h b/elf/tst-unique3.h
deleted file mode 100644
index 716d23641c..0000000000
--- a/elf/tst-unique3.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// BZ 12510
-template<typename T>
-struct S
-{
- static int i;
-};
-
-extern int in_lib (void);
diff --git a/elf/tst-unique3lib.cc b/elf/tst-unique3lib.cc
deleted file mode 100644
index fa8e85a36c..0000000000
--- a/elf/tst-unique3lib.cc
+++ /dev/null
@@ -1,11 +0,0 @@
-#include <cstdio>
-#include "tst-unique3.h"
-template<typename T> int S<T>::i = 1;
-static int i = S<char>::i;
-
-int
-in_lib (void)
-{
- std::printf ("in_lib: %d %d\n", S<char>::i, i);
- return S<char>::i++ != 2 || i != 1;
-}
diff --git a/elf/tst-unique3lib2.cc b/elf/tst-unique3lib2.cc
deleted file mode 100644
index 17d817e12e..0000000000
--- a/elf/tst-unique3lib2.cc
+++ /dev/null
@@ -1,12 +0,0 @@
-#include <cstdio>
-#include "tst-unique3.h"
-
-template<typename T> int S<T>::i;
-
-extern "C"
-int
-in_lib2 ()
-{
- std::printf ("in_lib2: %d\n", S<char>::i);
- return S<char>::i != 3;
-}
diff --git a/elf/tst-unique4.cc b/elf/tst-unique4.cc
deleted file mode 100644
index 575c70d3a1..0000000000
--- a/elf/tst-unique4.cc
+++ /dev/null
@@ -1,28 +0,0 @@
-// BZ 12511
-#include "tst-unique4.h"
-
-#include <cstdio>
-
-static int a[24] =
- {
- S<1>::i, S<2>::i, S<3>::i, S<4>::i, S<5>::i, S<6>::i, S<7>::i, S<8>::i,
- S<9>::i, S<10>::i, S<11>::i, S<12>::i, S<13>::i, S<14>::i, S<15>::i,
- S<16>::i, S<17>::i, S<18>::i, S<19>::i, S<20>::i, S<21>::i, S<22>::i,
- S<23>::i, S<24>::i
- };
-
-int
-main (void)
-{
- int result = 0;
- for (int i = 0; i < 24; ++i)
- {
- printf("%d ", a[i]);
- result |= a[i] != i + 1;
- }
-
- printf("\n%d\n", S<1>::j);
- result |= S<1>::j != -1;
-
- return result;
-}
diff --git a/elf/tst-unique4.h b/elf/tst-unique4.h
deleted file mode 100644
index 2d377f5d51..0000000000
--- a/elf/tst-unique4.h
+++ /dev/null
@@ -1,7 +0,0 @@
-// BZ 12511
-template<int N>
-struct S
-{
- static int i;
- static const int j;
-};
diff --git a/elf/tst-unique4lib.cc b/elf/tst-unique4lib.cc
deleted file mode 100644
index 17a7cdf567..0000000000
--- a/elf/tst-unique4lib.cc
+++ /dev/null
@@ -1,17 +0,0 @@
-// BZ 12511
-#include "tst-unique4.h"
-
-template<int N>
-int S<N>::i = N;
-template<int N>
-const int S<N>::j __attribute__ ((used)) = -1;
-
-static int a[24] __attribute__ ((used)) =
- {
- S<1>::i, S<2>::i, S<3>::i, S<4>::i, S<5>::i, S<6>::i, S<7>::i, S<8>::i,
- S<9>::i, S<10>::i, S<11>::i, S<12>::i, S<13>::i, S<14>::i, S<15>::i,
- S<16>::i, S<17>::i, S<18>::i, S<19>::i, S<20>::i, S<21>::i, S<22>::i,
- S<23>::i, S<24>::i
- };
-
-static int b __attribute__ ((used)) = S<1>::j;
diff --git a/elf/unload.c b/elf/unload.c
deleted file mode 100644
index 4566f226f8..0000000000
--- a/elf/unload.c
+++ /dev/null
@@ -1,91 +0,0 @@
-/* Test for unloading (really unmapping) of objects. By Franz Sirl.
- This test does not have to passed in all dlopen() et.al. implementation
- since it is not required the unloading actually happens. But we
- require it for glibc. */
-
-#include <dlfcn.h>
-#include <link.h>
-#include <mcheck.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-#define OUT \
- for (map = MAPS; map != NULL; map = map->l_next) \
- if (map->l_type == lt_loaded) \
- printf ("name = \"%s\", direct_opencount = %d\n", \
- map->l_name, (int) map->l_direct_opencount); \
- fflush (stdout)
-
-typedef struct
-{
- void *next;
-} strct;
-
-int
-main (void)
-{
- void *sohandle;
- strct *testdat;
- int ret;
- int result = 0;
- struct link_map *map;
-
- mtrace ();
-
- puts ("\nBefore");
- OUT;
-
- sohandle = dlopen ("unloadmod.so", RTLD_NOW | RTLD_GLOBAL);
- if (sohandle == NULL)
- {
- printf ("*** first dlopen failed: %s\n", dlerror ());
- exit (1);
- }
-
- puts ("\nAfter loading unloadmod.so");
- OUT;
-
- testdat = dlsym (sohandle, "testdat");
- testdat->next = (void *) -1;
-
- ret = dlclose (sohandle);
- if (ret != 0)
- {
- puts ("*** first dlclose failed");
- result = 1;
- }
-
- puts ("\nAfter closing unloadmod.so");
- OUT;
-
- sohandle = dlopen ("unloadmod.so", RTLD_NOW | RTLD_GLOBAL);
- if (sohandle == NULL)
- {
- printf ("*** second dlopen failed: %s\n", dlerror ());
- exit (1);
- }
-
- puts ("\nAfter loading unloadmod.so the second time");
- OUT;
-
- testdat = dlsym (sohandle, "testdat");
- if (testdat->next == (void *) -1)
- {
- puts ("*** testdat->next == (void *) -1");
- result = 1;
- }
-
- ret = dlclose (sohandle);
- if (ret != 0)
- {
- puts ("*** second dlclose failed");
- result = 1;
- }
-
- puts ("\nAfter closing unloadmod.so again");
- OUT;
-
- return result;
-}
diff --git a/elf/unload2.c b/elf/unload2.c
deleted file mode 100644
index eef2bfd426..0000000000
--- a/elf/unload2.c
+++ /dev/null
@@ -1,59 +0,0 @@
-#include <dlfcn.h>
-#include <elf.h>
-#include <errno.h>
-#include <error.h>
-#include <link.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#define MAPS ((struct link_map *) _r_debug.r_map)
-
-#define OUT \
- for (map = MAPS; map != NULL; map = map->l_next) \
- if (map->l_type == lt_loaded) \
- printf ("name = \"%s\", direct_opencount = %d\n", \
- map->l_name, (int) map->l_direct_opencount); \
- fflush (stdout)
-
-int
-main (void)
-{
- void *h[3];
- struct link_map *map;
- void (*fp) (void);
-
- h[0] = dlopen ("unload2mod.so", RTLD_LAZY);
- h[1] = dlopen ("unload2mod.so", RTLD_LAZY);
- if (h[0] == NULL || h[1] == NULL)
- error (EXIT_FAILURE, errno, "cannot load \"unload2mod.so\"");
- h[2] = dlopen ("unload2dep.so", RTLD_LAZY);
- if (h[2] == NULL)
- error (EXIT_FAILURE, errno, "cannot load \"unload2dep.so\"");
-
- puts ("\nAfter loading everything:");
- OUT;
-
- dlclose (h[0]);
-
- puts ("\nAfter unloading \"unload2mod.so\" once:");
- OUT;
-
- dlclose (h[1]);
-
- puts ("\nAfter unloading \"unload2mod.so\" twice:");
- OUT;
-
- fp = dlsym (h[2], "foo");
- puts ("\nnow calling `foo'");
- fflush (stdout);
- fp ();
- puts ("managed to call `foo'");
- fflush (stdout);
-
- dlclose (h[2]);
-
- puts ("\nAfter unloading \"unload2dep.so\":");
- OUT;
-
- return 0;
-}
diff --git a/elf/unload2dep.c b/elf/unload2dep.c
deleted file mode 100644
index 0d319515d5..0000000000
--- a/elf/unload2dep.c
+++ /dev/null
@@ -1,6 +0,0 @@
-extern void foo (void);
-
-void
-foo (void)
-{
-}
diff --git a/elf/unload2mod.c b/elf/unload2mod.c
deleted file mode 100644
index 9c2ea586bc..0000000000
--- a/elf/unload2mod.c
+++ /dev/null
@@ -1,8 +0,0 @@
-extern void foo (void);
-extern void bar (void);
-
-void
-bar (void)
-{
- foo ();
-}
diff --git a/elf/unload3.c b/elf/unload3.c
deleted file mode 100644
index 6f1af707e6..0000000000
--- a/elf/unload3.c
+++ /dev/null
@@ -1,41 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *g = dlopen ("unload3mod1.so", RTLD_GLOBAL | RTLD_NOW);
- void *h = dlopen ("unload3mod2.so", RTLD_GLOBAL | RTLD_NOW);
- if (g == NULL || h == NULL)
- {
- printf ("dlopen unload3mod{1,2}.so failed: %p %p\n", g, h);
- return 1;
- }
- dlclose (h);
- dlclose (g);
-
- g = dlopen ("unload3mod3.so", RTLD_GLOBAL | RTLD_NOW);
- h = dlopen ("unload3mod4.so", RTLD_GLOBAL | RTLD_NOW);
- if (g == NULL || h == NULL)
- {
- printf ("dlopen unload3mod{3,4}.so failed: %p %p\n", g, h);
- return 1;
- }
-
- int (*fn) (int);
- fn = dlsym (h, "bar");
- if (fn == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
-
- int val = fn (16);
- if (val != 24)
- {
- printf ("bar returned %d != 24\n", val);
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/unload3mod1.c b/elf/unload3mod1.c
deleted file mode 100644
index e886b11c18..0000000000
--- a/elf/unload3mod1.c
+++ /dev/null
@@ -1 +0,0 @@
-int dummy1;
diff --git a/elf/unload3mod2.c b/elf/unload3mod2.c
deleted file mode 100644
index 03252a523b..0000000000
--- a/elf/unload3mod2.c
+++ /dev/null
@@ -1 +0,0 @@
-int dummy2;
diff --git a/elf/unload3mod3.c b/elf/unload3mod3.c
deleted file mode 100644
index 046022c55d..0000000000
--- a/elf/unload3mod3.c
+++ /dev/null
@@ -1,8 +0,0 @@
-#include <stdio.h>
-
-int
-foo (int x)
-{
- puts ("foo");
- return x * 2;
-}
diff --git a/elf/unload3mod4.c b/elf/unload3mod4.c
deleted file mode 100644
index 52f808e79b..0000000000
--- a/elf/unload3mod4.c
+++ /dev/null
@@ -1,13 +0,0 @@
-#include <stdio.h>
-
-extern int foo (int x);
-
-int
-bar (int x)
-{
- puts ("bar");
- fflush (stdout);
- x = foo (x - 4);
- puts ("bar after foo");
- return x;
-}
diff --git a/elf/unload4.c b/elf/unload4.c
deleted file mode 100644
index 6e171a22e0..0000000000
--- a/elf/unload4.c
+++ /dev/null
@@ -1,48 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <malloc.h>
-
-int
-main (void)
-{
-#ifdef M_PERTURB
- mallopt (M_PERTURB, 0xaa);
-#endif
-
- void *h;
- int (*fn) (int);
- h = dlopen ("unload4mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("1st dlopen failed");
- return 1;
- }
- fn = dlsym (h, "foo");
- if (fn == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
- int n = fn (10);
- if (n != 28)
- {
- printf ("foo (10) returned %d != 28\n", n);
- return 1;
- }
- dlclose (h);
- h = dlopen ("unload4mod3.so", RTLD_LAZY);
- fn = dlsym (h, "mod3fn2");
- if (fn == NULL)
- {
- puts ("second dlsym failed");
- return 1;
- }
- n = fn (10);
- if (n != 22)
- {
- printf ("mod3fn2 (10) returned %d != 22\n", n);
- return 1;
- }
- dlclose (h);
- return 0;
-}
diff --git a/elf/unload4mod1.c b/elf/unload4mod1.c
deleted file mode 100644
index 38c5b0168d..0000000000
--- a/elf/unload4mod1.c
+++ /dev/null
@@ -1,10 +0,0 @@
-#include <stdio.h>
-
-extern int bar (int);
-
-int
-foo (int x)
-{
- puts ("in foo");
- return bar (x / 2) + 2;
-}
diff --git a/elf/unload4mod2.c b/elf/unload4mod2.c
deleted file mode 100644
index 497ef5d93b..0000000000
--- a/elf/unload4mod2.c
+++ /dev/null
@@ -1,8 +0,0 @@
-#include <stdio.h>
-
-int
-baz (int x)
-{
- puts ("in baz");
- return x * 4;
-}
diff --git a/elf/unload4mod3.c b/elf/unload4mod3.c
deleted file mode 100644
index 4b280bc05b..0000000000
--- a/elf/unload4mod3.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-
-int
-__attribute__((noinline))
-mod3fn1 (int x)
-{
- puts ("in mod3fn1");
- return x + 6;
-}
-
-int
-mod3fn2 (int x)
-{
- puts ("in mod3fn2");
- return mod3fn1 (x / 2) * 2;
-}
diff --git a/elf/unload4mod4.c b/elf/unload4mod4.c
deleted file mode 100644
index ba5a144d38..0000000000
--- a/elf/unload4mod4.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <stdio.h>
-#include <stdlib.h>
-
-int
-__attribute__((noinline))
-baz (int x)
-{
- abort ();
-}
-
-int
-bar (int x)
-{
- puts ("in bar");
- return baz (x + 1) + 2;
-}
diff --git a/elf/unload5.c b/elf/unload5.c
deleted file mode 100644
index 0555052ce8..0000000000
--- a/elf/unload5.c
+++ /dev/null
@@ -1,42 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *g = dlopen ("unload3mod1.so", RTLD_GLOBAL | RTLD_NOW);
- void *h = dlopen ("unload3mod2.so", RTLD_GLOBAL | RTLD_NOW);
- if (g == NULL || h == NULL)
- {
- printf ("dlopen unload3mod{1,2}.so failed: %p %p\n", g, h);
- return 1;
- }
- dlopen ("unload3mod4.so", RTLD_GLOBAL | RTLD_NOW);
- dlclose (h);
- dlclose (g);
-
- g = dlopen ("unload3mod3.so", RTLD_GLOBAL | RTLD_NOW);
- h = dlopen ("unload3mod4.so", RTLD_GLOBAL | RTLD_NOW);
- if (g == NULL || h == NULL)
- {
- printf ("dlopen unload3mod{3,4}.so failed: %p %p\n", g, h);
- return 1;
- }
-
- int (*fn) (int);
- fn = dlsym (h, "bar");
- if (fn == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
-
- int val = fn (16);
- if (val != 24)
- {
- printf ("bar returned %d != 24\n", val);
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/unload6.c b/elf/unload6.c
deleted file mode 100644
index 1efc7eb841..0000000000
--- a/elf/unload6.c
+++ /dev/null
@@ -1,30 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *h = dlopen ("unload6mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload6mod1.so failed");
- return 1;
- }
-
- int (*fn) (int);
- fn = dlsym (h, "foo");
- if (fn == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
-
- int val = fn (16);
- if (val != 24)
- {
- printf ("foo returned %d != 24\n", val);
- return 1;
- }
-
- return 0;
-}
diff --git a/elf/unload6mod1.c b/elf/unload6mod1.c
deleted file mode 100644
index 24f2e5a19a..0000000000
--- a/elf/unload6mod1.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-foo (int i)
-{
- void *h = dlopen ("unload6mod2.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload6mod2.so failed");
- return 1;
- }
-
- dlclose (h);
- return i + 8;
-}
diff --git a/elf/unload6mod2.c b/elf/unload6mod2.c
deleted file mode 100644
index 980efa4b0e..0000000000
--- a/elf/unload6mod2.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <unistd.h>
-
-static void *h;
-
-static void __attribute__((constructor))
-mod2init (void)
-{
- h = dlopen ("unload6mod3.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload6mod3.so failed");
- fflush (stdout);
- _exit (1);
- }
-}
-
-static void __attribute__((destructor))
-mod2fini (void)
-{
- dlclose (h);
-}
diff --git a/elf/unload6mod3.c b/elf/unload6mod3.c
deleted file mode 100644
index 7b29e1d626..0000000000
--- a/elf/unload6mod3.c
+++ /dev/null
@@ -1,23 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <unistd.h>
-
-static void *h;
-
-static void __attribute__((constructor))
-mod3init (void)
-{
- h = dlopen ("unload6mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload6mod1.so failed");
- fflush (stdout);
- _exit (1);
- }
-}
-
-static void __attribute__((destructor))
-mod3fini (void)
-{
- dlclose (h);
-}
diff --git a/elf/unload7.c b/elf/unload7.c
deleted file mode 100644
index 198f7db286..0000000000
--- a/elf/unload7.c
+++ /dev/null
@@ -1,39 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *h = dlopen ("$ORIGIN/unload7mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload7mod1.so failed");
- return 1;
- }
-
- int (*fn) (void);
- fn = dlsym (h, "foo");
- if (fn == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
-
- int ret = 0;
- if (fn () == 0)
- ++ret;
-
- void *h2 = dlopen ("$ORIGIN/unload7mod2.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("dlopen unload7mod2.so failed");
- return 1;
- }
- dlclose (h2);
-
- if (fn () == 0)
- ++ret;
-
- dlclose (h);
- return ret;
-}
diff --git a/elf/unload7mod1.c b/elf/unload7mod1.c
deleted file mode 100644
index 7435adce2c..0000000000
--- a/elf/unload7mod1.c
+++ /dev/null
@@ -1,11 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-foo (int i)
-{
- if (dlsym (RTLD_DEFAULT, "unload7_nonexistent_symbol") == NULL)
- return 1;
- puts ("dlsym returned non-NULL");
- return 0;
-}
diff --git a/elf/unload7mod2.c b/elf/unload7mod2.c
deleted file mode 100644
index 6d1a0d47b7..0000000000
--- a/elf/unload7mod2.c
+++ /dev/null
@@ -1 +0,0 @@
-int x;
diff --git a/elf/unload8.c b/elf/unload8.c
deleted file mode 100644
index f984a38098..0000000000
--- a/elf/unload8.c
+++ /dev/null
@@ -1,33 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-
-int
-main (void)
-{
- void *h = dlopen ("$ORIGIN/unload8mod1.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload8mod1.so failed");
- return 1;
- }
-
- void *h2 = dlopen ("$ORIGIN/unload8mod1x.so", RTLD_LAZY);
- if (h2 == NULL)
- {
- puts ("dlopen unload8mod1x.so failed");
- return 1;
- }
- dlclose (h2);
-
- int (*mod1) (void) = dlsym (h, "mod1");
- if (mod1 == NULL)
- {
- puts ("dlsym failed");
- return 1;
- }
-
- mod1 ();
- dlclose (h);
-
- return 0;
-}
diff --git a/elf/unload8mod1.c b/elf/unload8mod1.c
deleted file mode 100644
index fe7e81c1c3..0000000000
--- a/elf/unload8mod1.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern void mod2 (void);
-
-void
-mod1 (void)
-{
- mod2 ();
-}
diff --git a/elf/unload8mod1x.c b/elf/unload8mod1x.c
deleted file mode 100644
index 835b634914..0000000000
--- a/elf/unload8mod1x.c
+++ /dev/null
@@ -1 +0,0 @@
-int mod1x;
diff --git a/elf/unload8mod2.c b/elf/unload8mod2.c
deleted file mode 100644
index 2fd8b6768a..0000000000
--- a/elf/unload8mod2.c
+++ /dev/null
@@ -1,7 +0,0 @@
-extern void mod3 (void);
-
-void
-mod2 (void)
-{
- mod3 ();
-}
diff --git a/elf/unload8mod3.c b/elf/unload8mod3.c
deleted file mode 100644
index d49e22b24c..0000000000
--- a/elf/unload8mod3.c
+++ /dev/null
@@ -1,27 +0,0 @@
-#include <dlfcn.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-void
-mod3_fini2 (void)
-{
-}
-
-void
-mod3_fini (void)
-{
- mod3_fini2 ();
-}
-
-void
-mod3 (void)
-{
- void *h = dlopen ("$ORIGIN/unload8mod2.so", RTLD_LAZY);
- if (h == NULL)
- {
- puts ("dlopen unload8mod2.so failed");
- exit (1);
- }
-
- atexit (mod3_fini);
-}
diff --git a/elf/unloadmod.c b/elf/unloadmod.c
deleted file mode 100644
index 3aa5403edf..0000000000
--- a/elf/unloadmod.c
+++ /dev/null
@@ -1,4 +0,0 @@
-struct testdat
-{
- void *next;
-} testdat;
diff --git a/elf/vismain.c b/elf/vismain.c
deleted file mode 100644
index 43f1d8f095..0000000000
--- a/elf/vismain.c
+++ /dev/null
@@ -1,260 +0,0 @@
-/* Copyright (C) 2000-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-/* This file must be compiled as PIE to avoid copy relocation when
- accessing protected symbols defined in shared libaries since copy
- relocation doesn't work with protected symbols and linker in
- binutils 2.26 enforces this rule. */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "vismod.h"
-
-/* Prototype for our test function. */
-extern int do_test (void);
-
-
-/* This defines the `main' function and some more. */
-#include <support/test-driver.c>
-
-
-/* Prototypes for local functions. */
-extern int protlocal (void);
-
-const char *protvarlocal = __FILE__;
-extern const char *protvarinmod;
-extern const char *protvaritcpt;
-
-int
-do_test (void)
-{
- int res = 0;
- int val;
-
- /* First test: check whether .protected is handled correctly by the
- assembler/linker. The uses of `protlocal' in the DSOs and in the
- main program should all be resolved with the local definitions. */
- val = protlocal () + calllocal1 () + calllocal2 ();
- if (val != 0x155)
- {
- puts ("\
-The handling of `.protected' seems to be implemented incorrectly: giving up");
- abort ();
- }
- puts ("`.protected' seems to be handled correctly, good!");
-
- /* Function pointers: for functions which are marked local and for
- which definitions are available all function pointers must be
- distinct. */
- if (protlocal == getlocal1 ())
- {
- puts ("`protlocal' in main and mod1 have same address");
- res = 1;
- }
- if (protlocal == getlocal2 ())
- {
- puts ("`protlocal' in main and mod2 have same address");
- res = 1;
- }
- if (getlocal1 () == getlocal2 ())
- {
- puts ("`protlocal' in mod1 and mod2 have same address");
- res = 1;
- }
- if (getlocal1 () () + getlocal2 () () != 0x44)
- {
- puts ("pointers to `protlocal' in mod1 or mod2 incorrect");
- res = 1;
- }
-
- /* Next test. This is similar to the last one but the function we
- are calling is not defined in the main object. This means that
- the invocation in the main object uses the definition in the
- first DSO. */
- if (protinmod != getinmod1 ())
- {
- printf ("&protinmod in main (%p) != &protinmod in mod1 (%p)\n",
- protinmod, getinmod1 ());
- res = 1;
- }
- if (protinmod == getinmod2 ())
- {
- puts ("`protinmod' in main and mod2 have same address");
- res = 1;
- }
- if (getinmod1 () == getinmod2 ())
- {
- puts ("`protinmod' in mod1 and mod2 have same address");
- res = 1;
- }
- if (protinmod () + getinmod1 () () + getinmod2 () () != 0x4800)
- {
- puts ("pointers to `protinmod' in mod1 or mod2 incorrect");
- res = 1;
- }
- val = protinmod () + callinmod1 () + callinmod2 ();
- if (val != 0x15800)
- {
- printf ("calling of `protinmod' leads to wrong result (%#x)\n", val);
- res = 1;
- }
-
- /* A very similar text. Same setup for the main object and the modules
- but this time we have another definition in a preloaded module. This
- one intercepts the references from the main object. */
- if (protitcpt != getitcpt3 ())
- {
- printf ("&protitcpt in main (%p) != &protitcpt in mod3 (%p)\n",
- &protitcpt, getitcpt3 ());
- res = 1;
- }
- if (protitcpt == getitcpt1 ())
- {
- puts ("`protitcpt' in main and mod1 have same address");
- res = 1;
- }
- if (protitcpt == getitcpt2 ())
- {
- puts ("`protitcpt' in main and mod2 have same address");
- res = 1;
- }
- if (getitcpt1 () == getitcpt2 ())
- {
- puts ("`protitcpt' in mod1 and mod2 have same address");
- res = 1;
- }
- val = protitcpt () + getitcpt1 () () + getitcpt2 () () + getitcpt3 () ();
- if (val != 0x8440000)
- {
- printf ("\
-pointers to `protitcpt' in mod1 or mod2 or mod3 incorrect (%#x)\n", val);
- res = 1;
- }
- val = protitcpt () + callitcpt1 () + callitcpt2 () + callitcpt3 ();
- if (val != 0x19540000)
- {
- printf ("calling of `protitcpt' leads to wrong result (%#x)\n", val);
- res = 1;
- }
-
- /* Now look at variables. First a variable which is available
- everywhere. We must have three different addresses. */
- if (&protvarlocal == getvarlocal1 ())
- {
- puts ("`protvarlocal' in main and mod1 have same address");
- res = 1;
- }
- if (&protvarlocal == getvarlocal2 ())
- {
- puts ("`protvarlocal' in main and mod2 have same address");
- res = 1;
- }
- if (getvarlocal1 () == getvarlocal2 ())
- {
- puts ("`protvarlocal' in mod1 and mod2 have same address");
- res = 1;
- }
- if (strcmp (protvarlocal, __FILE__) != 0)
- {
- puts ("`protvarlocal in main has wrong value");
- res = 1;
- }
- if (strcmp (*getvarlocal1 (), "vismod1.c") != 0)
- {
- puts ("`getvarlocal1' returns wrong value");
- res = 1;
- }
- if (strcmp (*getvarlocal2 (), "vismod2.c") != 0)
- {
- puts ("`getvarlocal2' returns wrong value");
- res = 1;
- }
-
- /* Now the case where there is no local definition. */
- if (&protvarinmod != getvarinmod1 ())
- {
- printf ("&protvarinmod in main (%p) != &protitcpt in mod1 (%p)\n",
- &protvarinmod, getvarinmod1 ());
- // XXX Possibly enable once fixed.
- // res = 1;
- }
- if (&protvarinmod == getvarinmod2 ())
- {
- puts ("`protvarinmod' in main and mod2 have same address");
- res = 1;
- }
- if (strcmp (*getvarinmod1 (), "vismod1.c") != 0)
- {
- puts ("`getvarinmod1' returns wrong value");
- res = 1;
- }
- if (strcmp (*getvarinmod2 (), "vismod2.c") != 0)
- {
- puts ("`getvarinmod2' returns wrong value");
- res = 1;
- }
-
- /* And a test where a variable definition is intercepted. */
- if (&protvaritcpt == getvaritcpt1 ())
- {
- puts ("`protvaritcpt' in main and mod1 have same address");
- res = 1;
- }
- if (&protvaritcpt == getvaritcpt2 ())
- {
- puts ("`protvaritcpt' in main and mod2 have same address");
- res = 1;
- }
- if (&protvaritcpt != getvaritcpt3 ())
- {
- printf ("&protvaritcpt in main (%p) != &protvaritcpt in mod3 (%p)\n",
- &protvaritcpt, getvaritcpt3 ());
- // XXX Possibly enable once fixed.
- // res = 1;
- }
- if (getvaritcpt1 () == getvaritcpt2 ())
- {
- puts ("`protvaritcpt' in mod1 and mod2 have same address");
- res = 1;
- }
- if (strcmp (protvaritcpt, "vismod3.c") != 0)
- {
- puts ("`protvaritcpt in main has wrong value");
- res = 1;
- }
- if (strcmp (*getvaritcpt1 (), "vismod1.c") != 0)
- {
- puts ("`getvaritcpt1' returns wrong value");
- res = 1;
- }
- if (strcmp (*getvaritcpt2 (), "vismod2.c") != 0)
- {
- puts ("`getvaritcpt2' returns wrong value");
- res = 1;
- }
-
- return res;
-}
-
-
-int
-protlocal (void)
-{
- return 0x1;
-}
diff --git a/elf/vismod.h b/elf/vismod.h
deleted file mode 100644
index ef05ffd5e9..0000000000
--- a/elf/vismod.h
+++ /dev/null
@@ -1,27 +0,0 @@
-/* Prototypes for the functions in the DSOs. */
-extern int calllocal1 (void);
-extern int (*getlocal1 (void)) (void);
-extern int callinmod1 (void);
-extern int (*getinmod1 (void)) (void);
-extern int callitcpt1 (void);
-extern int (*getitcpt1 (void)) (void);
-extern const char **getvarlocal1 (void);
-extern const char **getvarinmod1 (void);
-extern const char **getvaritcpt1 (void);
-extern int calllocal2 (void);
-extern int (*getlocal2 (void)) (void);
-extern int callinmod2 (void);
-extern int (*getinmod2 (void)) (void);
-extern int callitcpt2 (void);
-extern int (*getitcpt2 (void)) (void);
-extern const char **getvarlocal2 (void);
-extern const char **getvarinmod2 (void);
-extern const char **getvaritcpt2 (void);
-extern int callitcpt3 (void);
-extern int (*getitcpt3 (void)) (void);
-extern const char **getvaritcpt3 (void);
-
-extern int protinmod (void);
-extern int protitcpt (void);
-extern int protlocal (void);
-
diff --git a/elf/vismod1.c b/elf/vismod1.c
deleted file mode 100644
index 3e56404ce7..0000000000
--- a/elf/vismod1.c
+++ /dev/null
@@ -1,103 +0,0 @@
-/* Copyright (C) 2000-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "vismod.h"
-
-int
-protlocal (void)
-{
- return 0x4;
-}
-asm (".protected protlocal");
-
-
-int
-calllocal1 (void)
-{
- return protlocal () + 0x10;
-}
-
-int
-(*getlocal1 (void)) (void)
-{
- return protlocal;
-}
-
-int
-protinmod (void)
-{
- return 0x400;
-}
-asm (".protected protinmod");
-
-int
-callinmod1 (void)
-{
- return protinmod () + 0x1000;
-}
-
-int
-(*getinmod1 (void)) (void)
-{
- return protinmod;
-}
-
-int
-protitcpt (void)
-{
- return 0x40000;
-}
-asm (".protected protitcpt");
-
-int
-callitcpt1 (void)
-{
- return protitcpt () + 0x100000;
-}
-
-int
-(*getitcpt1 (void)) (void)
-{
- return protitcpt;
-}
-
-const char *protvarlocal = __FILE__;
-asm (".protected protvarlocal");
-
-const char **
-getvarlocal1 (void)
-{
- return &protvarlocal;
-}
-
-const char *protvarinmod = __FILE__;
-asm (".protected protvarinmod");
-
-const char **
-getvarinmod1 (void)
-{
- return &protvarinmod;
-}
-
-const char *protvaritcpt = __FILE__;
-asm (".protected protvaritcpt");
-
-const char **
-getvaritcpt1 (void)
-{
- return &protvaritcpt;
-}
diff --git a/elf/vismod2.c b/elf/vismod2.c
deleted file mode 100644
index 89be69728a..0000000000
--- a/elf/vismod2.c
+++ /dev/null
@@ -1,123 +0,0 @@
-/* Copyright (C) 2000-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include <stdlib.h>
-#include "vismod.h"
-
-int
-protlocal (void)
-{
- return 0x40;
-}
-asm (".protected protlocal");
-
-
-int
-calllocal2 (void)
-{
- return protlocal () + 0x100;
-}
-
-int
-(*getlocal2 (void)) (void)
-{
- return protlocal;
-}
-
-int
-protinmod (void)
-{
- return 0x4000;
-}
-asm (".protected protinmod");
-
-int
-callinmod2 (void)
-{
- return protinmod () + 0x10000;
-}
-
-int
-(*getinmod2 (void)) (void)
-{
- return protinmod;
-}
-
-int
-protitcpt (void)
-{
- return 0x400000;
-}
-asm (".protected protitcpt");
-
-int
-callitcpt2 (void)
-{
- return protitcpt () + 0x1000000;
-}
-
-int
-(*getitcpt2 (void)) (void)
-{
- return protitcpt;
-}
-
-const char *protvarlocal = __FILE__;
-asm (".protected protvarlocal");
-
-const char **
-getvarlocal2 (void)
-{
- return &protvarlocal;
-}
-
-const char *protvarinmod = __FILE__;
-asm (".protected protvarinmod");
-
-const char **
-getvarinmod2 (void)
-{
- return &protvarinmod;
-}
-
-const char *protvaritcpt = __FILE__;
-asm (".protected protvaritcpt");
-
-const char **
-getvaritcpt2 (void)
-{
- return &protvaritcpt;
-}
-
-/* We must never call these functions. */
-int
-callitcpt3 (void)
-{
- abort ();
-}
-
-int
-(*getitcpt3 (void)) (void)
-{
- abort ();
-}
-
-const char **
-getvaritcpt3 (void)
-{
- abort ();
-}
diff --git a/elf/vismod3.c b/elf/vismod3.c
deleted file mode 100644
index 1074d1bcda..0000000000
--- a/elf/vismod3.c
+++ /dev/null
@@ -1,46 +0,0 @@
-/* Copyright (C) 2000-2017 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "vismod.h"
-
-int
-protitcpt (void)
-{
- return 0x4000000;
-}
-asm (".protected protitcpt");
-
-int
-callitcpt3 (void)
-{
- return protitcpt () + 0x10000000;
-}
-
-int
-(*getitcpt3 (void)) (void)
-{
- return protitcpt;
-}
-
-const char *protvaritcpt = __FILE__;
-asm (".protected protvaritcpt");
-
-const char **
-getvaritcpt3 (void)
-{
- return &protvaritcpt;
-}