-
Notifications
You must be signed in to change notification settings - Fork 1.1k
build: Add SECP256K1_FORCE_HIDDEN_VISIBILITY #1677
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
build: Add SECP256K1_FORCE_HIDDEN_VISIBILITY #1677
Conversation
aa2448a
to
5f8dbfe
Compare
include/secp256k1.h
Outdated
* | ||
* While visibility is a concept that applies only to shared libraries, setting | ||
* visibility will still make a difference when building a static library: the | ||
* visibility settings will be stored in the static library, solely for the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Mind sharing more details regarding "the visibility settings will be stored in the static library" please?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
See https://stackoverflow.com/a/67473340/2725281. I don't think I have more to share, but I assume @theuni can confirm the behavior.
Like #1674, this defaults to "default" (haha) visibility. While not perfect for static builds -- we'd probably prefer a default of "hidden" there -- this avoids any attempt to detection in the preprocessor whether a static or a shared library is built. Some kind of detection is possible (see my comment in #1674), but it will most likely never be perfect, and some manual override will be necessary anyway. Defaulting to "default" avoids the need to detect and is thus much simpler. |
Hmm. There's a pretty common assumption that when using So I think many packagers would run into problems with this, as that flag (which is usually considered safe for visibility-aware libs) would essentially produce broken shared libs (except on Windows). |
Hm, that assumption sounds misguided to me. If a packager expects a visibility-aware lib, they should let the lib set the flags... Whatever, I think it's easy to address this concern by setting "default" in an else branch: #ifndef SECP256K1_API
# if defined(__GNUC__) && (__GNUC__ >= 4) && defined(SECP256K1_BUILD)
# if defined(SECP256K1_FORCE_HIDDEN_VISIBILITY)
# define SECP256K1_API extern __attribute__ ((visibility ("hidden")))
# else
# define SECP256K1_API extern __attribute__ ((visibility ("default")))
# endif
# endif
#endif What do you think? |
libsecp's in a pretty unique position here because it has no private non-static functions and only a handful of private vars. Most libs have a huge pile of functions and marking them all as hidden would be infeasible. Hence the compiler flag/default override combo. Edit:
Sure, it's not conventional, but it gets the job done :) |
Ok, I can update the PR tomorrow. :)
Yep. So for visibility-aware libs, it's a noop, and for non-aware libs, it breaks the build. Sounds like an option you don't wanna have in your toolchain file. ;) Okay, just kidding, I guess there may be aware libs which leave setting the compiler detault to the user. |
Not sure yet what to think of the two approaches, but it does strike me as very unfortunate that we are introducing more bespoke behaviour yet again. Can we at least only allow this being set when |
I am not sure how bespoke this is, in the end. I think the ability to configure visibility for static builds is a valid use case in general, not specific to Bitcoin Core's planned use. It's just pretty niche... (That's different from #1678, which is merely a hack that works around a lack of functionality in CMake.) edit: But if the goal is to avoid the need for any of these, then I believe the proper way is to abandon the idea of building a monolithic kernel. IIUC, then you won't need to the CMake workaround, and you can use
In both PRs, the override is currently just an |
The name should make it clear that this is intended for ELF platforms only.
5f8dbfe
to
42d3133
Compare
Force-pushed this update. Here's another variant of that approach: real-or-random@2d92ac3 Instead of an override to force "hidden", this has an override to do nothing. Then the user can use |
* solely for the potential case that the static library will be linked into | ||
* a shared library. In that case, the stored visibility settings will | ||
* resurface and be honored for the shared library. */ | ||
# define SECP256K1_API extern __attribute__ ((visibility("hidden"))) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Win32 needs this branch too, no? Otherwise it'll still require -fvisibility=hidden
for static libs?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, maybe #if defined(SECP256K1_FORCE_HIDDEN_VISIBILITY)
could just go at the top, and keep with the #ifndef(SECP256K1_API)
pattern below it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Win32 needs this branch too, no? Otherwise it'll still require
-fvisibility=hidden
for static libs?
I don't think so (but I haven't tested this so far). As far as I understand, gcc defaults to hidden on Windows as soon as it sees an explicit __declspec(dllexport)
annotation (and MSVC anyway exports only annotated symbols). At least this is what the libtool manual claims:
It should be noted that the GNU auto-export feature is turned off when an explicit
__declspec(dllexport)
is seen. The GNU tools do this to not make more symbols visible for projects that have already taken the trouble to decorate symbols.
https://www.gnu.org/software/libtool/manual/html_node/Windows-DLLs.html
Actually, maybe
#if defined(SECP256K1_FORCE_HIDDEN_VISIBILITY)
could just go at the top, and keep with the#ifndef(SECP256K1_API)
pattern below it?
Not sure if I can follow. If you still think we'll need this for Windows, can you suggest/sketch a patch?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No worries.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ACK 42d3133
Alternative to #1674.