Sure I can remember. Checking libraries the binary uses ("why this cURL fails
on HTTPs? oh, it's linked against GnuTLS, that explains everything"),
injecting your own library, intercepting a function (maybe syscall, or rather
its libc wrapper), tracing function's execution (ltrace). All these things
merely annoy if you used to have them but now you don't and it's hard to
remember them all, but there's a lot of them.
And then there's also sharing memory between different processes that use the
same library. You don't have that for a statically compiled binary.
All those things sound like antipatterns to me. If your application is supposed to fetch HTTPS pages then there should be an integration test for that, so you would never have to debug it in production. Having shared objects on the machine actually makes this impossible because your tests are running with different libraries than in production. Shared libraries on a machine are a non-hermetic input to your build and are to be avoided. In addition, runtime shared objects (especially of something performance-critical like crypto) inhibit all of the most important compiler optimizations like inlining. The savings from sharing text segments is small in my experience. As for ltrace, there's a million ways to trace function calls these days, like uprobe or perf.
> All those things sound like antipatterns to me. If your application is supposed to fetch HTTPS pages then there should be an integration test for that [...]
It's not something to regularly rely on, but something that helps in debugging
and troubleshooting. Not for a programmer, but for a sysadmin.
> Having shared objects on the machine actually makes this impossible because your tests are running with different libraries than in production.
In such a case you have your deployment process broken. And if your testing
and production environments differ in this matter, they differ enough bite
your ass even with your statically linked binary.
> Shared libraries on a machine are a non-hermetic input to your build and are to be avoided.
This is merely stating a generic opinion. I want to see a concrete, coherent,
technical argument supporting this.
> In addition, runtime shared objects (especially of something performance-critical like crypto) inhibit all of the most important compiler optimizations like inlining.
Especially crypto should not be called in a tight loop, but passed a large
chunk of data. Otherwise you inhibit all of the most important defence
against side channel attacks, and I guarantee that you are not competent
enough to defent against that on your own.
> As for ltrace, there's a million ways to trace function calls these days, like uprobe or perf.
So let's break one of them for no good reason?
And still, lack of any of the mentioned things is merely an annoyance once you
hit it, but as I said, they are numerous and add up, while the other option,
static linking, provides little benefit apart from supporting broken workflows
(like different environment in testing and production).
And then there's also sharing memory between different processes that use the same library. You don't have that for a statically compiled binary.