Dynamic Linking
harmful.cat-v.org
harmful.cat-v.org
Here's a killer application of dynamic linking: NSS. It's wonderful to be able to extend applications with new notions of names and addresses.
Remember the bad old days when /etc/passwd parsing was hardcoded and you had a choice of either local users or NIS, and that choice was baked into every application? PAM is another good example.
By the way: there's no such thing as static linking in Windows. All system calls go through ntdll.dll. (In fact, the actual system call numbers are scrambled with every service pack.) This property allows wonderful things, including a pure _userspace_ implementation of 32-bit compatibility for an otherwise pure 64-bit kernel.
Holy fuck, this is one of the most absurd exaggerations I've read in some time. I'm assuming you have a very strong and convincing reason to justify this statement.
Here's a killer application of dynamic linking: NSS.
...
Really? NSS?
OK, so static NIS/YP may not be good at all, but that doesn't change that NSS and the nscd (name server cache daemon) have been amongst the buggiest and most brittle components in glibc, on top of glibc's sequential DNS resolution. It's so bad the Busybox developers had to write a single-threaded fork-based alternative just to deal with its inherent resource exhaustion issues (see the comments in this software: http://busybox.net/~vda/unscd/).
And this: http://www.nico.schottelius.org/blog/nscd-bugs/
musl libc (ever growing in popularity in embedded and other fields for its standards compliance, robustness and implementation simplicity) doesn't support NSS and doesn't intend to, instead researching several alternative methods, the third one probably optimal: http://wiki.musl-libc.org/wiki/Open_Issues#NIS.2FLDAP.2Fothe...
And if you think this problem hasn't been solved so much more elegantly before, look into the details of Plan 9's ndb and factotum.
PAM is another good example.
bsd_auth is much better: http://www.openbsd.org/cgi-bin/man.cgi/OpenBSD-current/man3/...
I'm conflicted on Musl. I like the idea. I like the focus on robustness. I like Felker's style [1]. But for God's sake, Musl refuses to implement basic operating system primitives we've had for decades, like dlclose(3), all because the author, from his necessarily limited perspective, just can't understand why someone would want those facilities.
I'm sticking with glibc until the Musl people decide they want robustness and feature parity.
By the way: PAM isn't "add in the bloat of additional backends". Dynamic loading of backends is the opposite of bloat.
There's absolutely no reason Felker can't greatly improve libc robustness and maintain at least source-level compatibility with a libc we've used for decades and that has many valuable features. Musl's sin is being gratuitously opinionated.
[1] http://ewontfix.com/, good for the most part. Wrong about 32-bit PIC being terrible. (What we really need is -fvisibility=hidden and -Bsymbolic by default.)
Some features aren't worth having parity with, or at least need to be well rethought - and Felker has had a good track record with the latter in terms of thread-local storage, UTF-8 and other properties, so I'm looking forward to how the musl community settles the question of name directories.
glibc, buggy and hacky as it is, doesn't try to impose its opinions on you.
No it doesn't. For example: we can fix the the glibc pthread_mutex_lock bug without affecting ABI or source compatibility.
Are you arguing that glibc code quality will magically go up if they abandon dynamic linking?
I'm not sure if you can blame glibc on bazaar practices. musl and glibc both have similar, BFDL-driven development models (well, glibc did until Drepper got booted, at least) yet musl has far better curation and attentiveness than glibc.
PAM and NSS have always been controversial (though PAM particularly) and better ways have been both developed and proposed.
With your statically linked system, you replace every single binary on your system that linked to openssl during build (if you can figure that out).
If you consider biological ecosystems, diverse genetics are almost always more robust against infection. You could potentially make that analogy about the ecosystem of computers as well.
For example, the systems I compile can all boot and function without the need for a dynamic linker. These static binaries are on a root filesystem that is in memory, not disk. Hence I can boot from removable media and then remove the media so the slot is open.
If I need larger, complex, dynamically linked programs I mount a filesystem that has them along with the dynamic linker and then chroot. I build these filesystems separately, usually storing them on removable media.
I'm sure the ldd problem could be solved by writing a slightly smarter "ldd" that doesn't actually execute the ELF binary, as well.
$ readelf -d ~/edev/trunk/src/emacs | grep NEEDED
0x0000000000000001 (NEEDED) Shared library: [libpthread.so.0]
0x0000000000000001 (NEEDED) Shared library: [libc.so.6]
0x0000000000000001 (NEEDED) Shared library: [libtiff.so.5]
0x0000000000000001 (NEEDED) Shared library: [libjpeg.so.8]
0x0000000000000001 (NEEDED) Shared library: [libpng12.so.0]
0x0000000000000001 (NEEDED) Shared library: [libgif.so.4]
0x0000000000000001 (NEEDED) Shared library: [libXpm.so.4]
0x0000000000000001 (NEEDED) Shared library: [libgtk-3.so.0]
0x0000000000000001 (NEEDED) Shared library: [libgdk-3.so.0]
0x0000000000000001 (NEEDED) Shared library: [libpango-1.0.so.0]
0x0000000000000001 (NEEDED) Shared library: [libcairo.so.2]
0x0000000000000001 (NEEDED) Shared library: [libgdk_pixbuf-2.0.so.0]
0x0000000000000001 (NEEDED) Shared library: [libgio-2.0.so.0]
0x0000000000000001 (NEEDED) Shared library: [libgobject-2.0.so.0]
0x0000000000000001 (NEEDED) Shared library: [libglib-2.0.so.0]
0x0000000000000001 (NEEDED) Shared library: [libSM.so.6]
0x0000000000000001 (NEEDED) Shared library: [libICE.so.6]
0x0000000000000001 (NEEDED) Shared library: [libX11.so.6]
0x0000000000000001 (NEEDED) Shared library: [libXrender.so.1]
0x0000000000000001 (NEEDED) Shared library: [libXft.so.2]
0x0000000000000001 (NEEDED) Shared library: [libasound.so.2]
0x0000000000000001 (NEEDED) Shared library: [librsvg-2.so.2]
0x0000000000000001 (NEEDED) Shared library: [libm.so.6]
0x0000000000000001 (NEEDED) Shared library: [libacl.so.1]
0x0000000000000001 (NEEDED) Shared library: [librt.so.1]
0x0000000000000001 (NEEDED) Shared library: [libdbus-1.so.3]
0x0000000000000001 (NEEDED) Shared library: [libXfixes.so.3]
0x0000000000000001 (NEEDED) Shared library: [libxml2.so.2]
0x0000000000000001 (NEEDED) Shared library: [libgpm.so.2]
0x0000000000000001 (NEEDED) Shared library: [libtinfo.so.5]
0x0000000000000001 (NEEDED) Shared library: [libgconf-2.so.4]
0x0000000000000001 (NEEDED) Shared library: [libselinux.so.1]
0x0000000000000001 (NEEDED) Shared library: [libfreetype.so.6]
0x0000000000000001 (NEEDED) Shared library: [libfontconfig.so.1]
0x0000000000000001 (NEEDED) Shared library: [libz.so.1]
0x0000000000000001 (NEEDED) Shared library: [libotf.so.0]
0x0000000000000001 (NEEDED) Shared library: [libm17n-core.so.0]
0x0000000000000001 (NEEDED) Shared library: [libm17n-flt.so.0]
0x0000000000000001 (NEEDED) Shared library: [libgnutls-deb0.so.28]You couldn't have picked a worse example. glibc goes to great lengths to maintain backward compatibility. glibc is practically the reason ELF symbol versions exist.
https://www.redhat.com/f/summitfiles/presentation/June2/Deve...
Or as it's generally said, the only software that never changes is software no one uses.
IMHO, the reluctance to "finish" a project and the stigma against something being "in maintenance mode" is responsible for most of the bloat and messes in modern software. Perhaps it's related to "CADT": http://www.jwz.org/doc/cadt.html
It's also, ironically, the cause of numerous security flaws. Maybe we wouldn't have to worry so much about security flaws in our libraries if we weren't constantly tearing them down and remaking them.
Regardless, in the case of libc, I genuinely cannot think of a reason to break binary compatibility, backwards or forward. The POSIX standard is set in stone, the interfaces are stable, the data types are opaque, etc. Of course you can create new implementations of memcpy etc that take advantage of new instruction sets, but I don't see why you need to break binary compatibility to do so.
Well, since you can't think of one, there must not be one.
You're right. Keep in mind, though, that we're living in a world where people ship applications built with dependencies like this:
deps = http://some.random.server.ru/some-library:1.4.4
and installation software like this: curl http://lol.hackme.cn | sudo bash
Do you expect people to really understand the nuances of security updates?With the "independent packaging" push using containers and dependency bundling, you get both downsides for the cost of one.
https://blogs.gnome.org/alexl/2015/02/17/first-fully-sandbox...
It's mystifying that the debate here centers around performance or RAM usage. The benefit of dynamic linking is architectural: it enables different components to evolve independently.
I understand Plan 9 has an unusual approach, where things that are traditionally library calls (getMousePosition) are instead filesystem operations (read /dev/mouse). But this seems terribly rigid to me: we've just replaced structs with a static byte stream format. How do you evolve this?
Albeit running on a VM as opposed to bare metal, and not actually currently statically linking everything.
It seems like we're trying to head that way.