<div dir="ltr">Wait, I have a terrible idea.  Why don't we roll our own .init_array style appending section?  I think we can make this work for all toolchains we support.<div><br></div><div>We'd have something like:<div>
<br></div><div>struct PODOptData {</div><div>  const char *FlagName;</div><div>...  // Common POD stuff, can be initialized at ParseCommandLine time.</div><div>};</div><div><br></div><div>LLVM_SECTION(".llvmopt")</div>
<div>PODOptData OptionRegisterer = { "foo_flag", ... };</div><div><br></div><div>I know the COFF magic to get the section bounds to form an array, and I know it exists for ELF, but I don't know how to do it on Darwin.</div>
<div><br></div></div></div><div class="gmail_extra"><br><br><div class="gmail_quote">On Tue, Sep 17, 2013 at 10:10 AM, Andrew Trick <span dir="ltr"><<a href="mailto:atrick@apple.com" target="_blank">atrick@apple.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">LLVM's internal command line library needs to evolve. We have an immediate need to build LLVM as a library free of static initializers, but before brute-force fixing this problem, I'd like outline the incremental steps that will lead to a desirable long term solution. We want infrastructure in place to provide an evolutionary path.<br>

<br>
In the near term, clients who need llvm-the-library with no static initializers will build with LLVM_NO_STATICINIT. In this mode, existing users of cl::opt will default to being optimized away as constant initializers, and those options will not be available for command line parsing.<br>

<br>
A new option class will need be defined, cl::toolopt. Initially, this will share the implementation and API with cl::opt. The only difference will be that cl::toolopt is immune to LLVM_NO_STATICINIT. Options that are required for tool support can simply be type-renamed to toolopt. Since these are not defined in a library, their static initializers are irrelevant.<br>

<br>
Eventually, we would like to eliminate the special LLVM_NO_STATICINIT build mode. This can be done by making the -Asserts build just as strict. In the meantime, we would like to run as many unit tests as possible with LLVM_NO_STATICINIT builds. This will be solved by gradually moving cl::opt definitions buried within LLVM libraries to to a new pattern that avoids static initialization.<br>

<br>
One easy pattern to follow is to register the option during pass initialization with all the convenient flags and parameters, but refer to a globally defined option storage that enforces the singleton and provides visibility. As long as pass initialization happens before parseCommandLine, usage should be consistent.<br>

<br>
Strawman:<br>
<br>
cl::optval<bool> MyOption; // Just the storage, no initialization.<br>
<br>
MyPass() {<br>
  // Only registers an option with the same optval once.<br>
  Option cl::registerOpt(MyOption, cl::init(false), cl::Hidden,<br>
                         cl::desc("Descriptive string..."), );<br>
}<br>
<br>
-Andy<br>
_______________________________________________<br>
LLVM Developers mailing list<br>
<a href="mailto:LLVMdev@cs.uiuc.edu">LLVMdev@cs.uiuc.edu</a>         <a href="http://llvm.cs.uiuc.edu" target="_blank">http://llvm.cs.uiuc.edu</a><br>
<a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev" target="_blank">http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev</a><br>
</blockquote></div><br></div>