@Gankra The swift dynamic linking article is on HN again and I’m still mad that you didn’t say “where Rustn’t” in the title.

@steve write your own followup article where you detail how Swift's ABI and Library Evolution works in EXCRUCIATINGLY PRECISE terms so you have an excuse to make a better title

@Gankra @steve “Templated C++ functions cannot have their implementations dynamically linked.” wait this isn’t true though? PCL uses external templates a bunch in concert with a explicit instantiations to speed up compile times via dynamic linking the template implementations

@Gankra @steve it’s an absolutely ginormous foot gun but there’s nothing stopping you from doing in! (And even regular templates are dynamically linked in that their symbols are weakly recorded and the runtime linker arbitrarily throws out N-1 of the N addresses rather than complaining about duplicate symbols)

@Gankra @steve (this is actually what “inline” means in modern C++ - the ODR rule doesn’t apply, implemented as an ABI detail with weak symbols, and templates are all just implicitly inline)

@elfprince13 @steve did you really not read the paragraphs immediately following that statement

@steve @Gankra I literally stopped at that sentence to come be like “???”

@Gankra @steve yes I know you’re super fluent in ABI stuff, but that sentence is just factually incorrect as written, without at least a parenthetical about “in versions prior to C++11” or something

@elfprince13 @steve you're definitely right that I didn't know about the ODR thing and that it lets you dynamically link generic statics in C++, I only learned that a few weeks ago, coincidentally!

Of course the reason I learned that a few weeks ago was because someone was complaining to me that it doesn't actually work because windows(?) doesn't actually support it so if you're trying to write bare-minimum-portable software you can't use it and it may as well not exist :)

@elfprince13 @steve more importantly the claim is still true within the relevant context:

the code is defacto inline (you can't hide the impl from users) and each instantiation of the template is a different symbol/address/code (you can't shove uninstantiated foo<T> into a vtable).

those are the interesting/important properties for the usecases i discuss. statics having equal addresses is comparably... very whatever (though definitely useful if you need it).

@Gankra @steve The “can’t have virtual templates because you can’t generate sensible vtables” is a fun one that I had to recently explain to a Rustacean friend who writes C++ for me at work now. He was convinced Rust solved this problem and I was like “I know it hasn’t or someone would have authored a paper fixing it for C++23 with the same technique”, which led to a deep dive into Rust documentation to the definition of object-safe trait

@steve @Gankra you actually can hide the impl though with extern templates, it just limits the types that can ever be used with that template to the ones the library authors explicitly instantiated in the dynamic shared library code.

Follow

@Gankra @steve (which is one of the reasons it’s a massive foot gun - issues that should be compiler errors get promoted to linker errors)

@steve @Gankra the possibility for ODR nondeterminism with is one of the reasons you’re REALLY not supposed to provide specializations of std:: templates (except apparently specialization of std::hash is allowed as an extension point for your own types, and I think that’s the only allowed deviation)

Sign in to participate in the conversation
Mastodon

General topic personal server.