<html xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:w="urn:schemas-microsoft-com:office:word" xmlns:m="http://schemas.microsoft.com/office/2004/12/omml" xmlns="http://www.w3.org/TR/REC-html40">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
<meta name="Generator" content="Microsoft Word 15 (filtered medium)">
<style><!--
/* Font Definitions */
@font-face
{font-family:Courier;
panose-1:2 7 4 9 2 2 5 2 4 4;}
@font-face
{font-family:"Cambria Math";
panose-1:2 4 5 3 5 4 6 3 2 4;}
@font-face
{font-family:Calibri;
panose-1:2 15 5 2 2 2 4 3 2 4;}
@font-face
{font-family:Consolas;
panose-1:2 11 6 9 2 2 4 3 2 4;}
@font-face
{font-family:LucidaGrande;}
@font-face
{font-family:Courier-Bold;}
@font-face
{font-family:LucidaGrande-Bold;}
/* Style Definitions */
p.MsoNormal, li.MsoNormal, div.MsoNormal
{margin:0cm;
font-size:11.0pt;
font-family:"Calibri",sans-serif;}
a:link, span.MsoHyperlink
{mso-style-priority:99;
color:#0563C1;
text-decoration:underline;}
.MsoChpDefault
{mso-style-type:export-only;
font-size:10.0pt;}
@page WordSection1
{size:612.0pt 792.0pt;
margin:72.0pt 72.0pt 72.0pt 72.0pt;}
div.WordSection1
{page:WordSection1;}
--></style><!--[if gte mso 9]><xml>
<o:shapedefaults v:ext="edit" spidmax="1026" />
</xml><![endif]--><!--[if gte mso 9]><xml>
<o:shapelayout v:ext="edit">
<o:idmap v:ext="edit" data="1" />
</o:shapelayout></xml><![endif]-->
</head>
<body lang="EN-CA" link="#0563C1" vlink="#954F72" style="word-wrap:break-word">
<div class="WordSection1">
<p class="MsoNormal"><span style="mso-fareast-language:EN-US">Hello Riyaz,<o:p></o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US">I did indeed answer here:
<a href="https://lists.llvm.org/pipermail/llvm-dev/2021-February/148299.html">https://lists.llvm.org/pipermail/llvm-dev/2021-February/148299.html</a><o:p></o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US">If you have a fix, would you mind sending it on Phabricator please?<o:p></o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US">Thanks,<o:p></o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US">Alex.<o:p></o:p></span></p>
<p class="MsoNormal"><span style="mso-fareast-language:EN-US"><o:p> </o:p></span></p>
<div>
<div style="border:none;border-top:solid #E1E1E1 1.0pt;padding:3.0pt 0cm 0cm 0cm">
<p class="MsoNormal"><b><span lang="FR">De :</span></b><span lang="FR"> llvm-dev <llvm-dev-bounces@lists.llvm.org>
<b>De la part de</b> Riyaz Puthiyapurayil via llvm-dev<br>
<b>Envoyé :</b> March 24, 2021 2:08 AM<br>
<b>À :</b> 'llvm-dev@lists.llvm.org' <llvm-dev@lists.llvm.org><br>
<b>Objet :</b> Re: [llvm-dev] CommandLine -- ResetAllOptionOccurrences with cl::bits -- Bug or by design?<o:p></o:p></span></p>
</div>
</div>
<p class="MsoNormal"><o:p> </o:p></p>
<p class="MsoNormal"><span lang="EN-US">I didn’t see a response. But I fixed this in our downstream code and it is working now as expected. It fixes two issues (1) clearing cl::bits and (2) allowing an optional storage location for cl::bits (the reinterpret_cast
is wrong for an enum to unsigned cast; it should be a static_cast). If there is interest in fixing this upstream, I can send the following patch for review (note, the following is for our downstream branch but I can put together a patch for master along with
some unit tests that expose the issue). <o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">diff --git a/llvm/include/llvm/Support/CommandLine.h b/llvm/include/llvm/Support/CommandLine.h<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">index 05374e3..712d6d3 100644<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">--- a/llvm/include/llvm/Support/CommandLine.h<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+++ b/llvm/include/llvm/Support/CommandLine.h<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">@@ -1720,7 +1720,7 @@ template <class DataType, class StorageClass> class bits_storage {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> unsigned *Location = nullptr; // Where to store the bits...<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> template <class T> static unsigned Bit(const T &V) {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">- unsigned BitPos = reinterpret_cast<unsigned>(V);<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ unsigned BitPos = static_cast<unsigned>(V);<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> assert(BitPos < sizeof(unsigned) * CHAR_BIT &&<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> "enum exceeds width of bit vector!");<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> return 1 << BitPos;<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">@@ -1744,6 +1744,11 @@ public:<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> unsigned getBits() { return *Location; }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ void clear() {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ if (Location)<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ *Location = 0;<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> template <class T> bool isSet(const T &V) {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> return (*Location & Bit(V)) != 0;<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">@@ -1767,6 +1772,8 @@ public:<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> unsigned getBits() { return Bits; }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ void clear() { Bits = 0; }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> template <class T> bool isSet(const T &V) { return (Bits & Bit(V)) != 0; }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">};<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">@@ -1813,7 +1820,7 @@ class bits : public Option, public bits_storage<DataType, Storage> {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> void printOptionValue(size_t /*GlobalWidth*/, bool /*Force*/) const override {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">- void setDefault() override {}<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">+ void setDefault() override { bits_storage<DataType, Storage>::clear(); }<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> void done() {<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> addArgument();<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<div>
<div style="border:none;border-top:solid #E1E1E1 1.0pt;padding:3.0pt 0cm 0cm 0cm">
<p class="MsoNormal"><b><span lang="EN-US">From:</span></b><span lang="EN-US"> Riyaz Puthiyapurayil
<br>
<b>Sent:</b> Sunday, March 21, 2021 4:30 PM<br>
<b>To:</b> <a href="mailto:llvm-dev@lists.llvm.org">llvm-dev@lists.llvm.org</a><br>
<b>Subject:</b> CommandLine -- ResetAllOptionOccurrences with cl::bits -- Bug or by design?<o:p></o:p></span></p>
</div>
</div>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US">I have some unit tests where I want to parse different command lines where some options use
</span><span lang="EN-US" style="font-family:Consolas">cl::bits</span><span lang="EN-US"> with an enum type. I want to reset the option occurrences in each unit test and reinvoke the command line parser with a new command line. While
</span><span lang="EN-US" style="font-family:Consolas">ResetAllOptionOccurrences</span><span lang="EN-US"> resets every other kind of option, it doesn’t do so for cl::bits. Is this by design?<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US">I see </span><span lang="EN-US" style="font-family:Consolas">setDefaultValue</span><span lang="EN-US"> of
</span><span lang="EN-US" style="font-family:Consolas">cl::bits</span><span lang="EN-US"> is an empty function. Why doesn’t it set the internal bit storage to 0 when ResetAllOptionOccurrences is called? I thought I could instead use an external storage and
set that to 0. But that doesn’t work either. It results in an error:<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">unsigned MyOptStorage;<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">static llvm::cl::bits<MyOpt,
<b>unsigned</b>> MyOpts(<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">….<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> llvm::cl::location(MyOptStorage),<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">…);<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas">include/llvm/Support/CommandLine.h:1723:23: error: reinterpret_cast from 'MyOpt’ to 'unsigned int' is not allowed<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-family:Consolas"> unsigned BitPos = reinterpret_cast<unsigned>(V);<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US">where ‘</span><span lang="EN-US" style="font-family:Consolas">MyOpt</span><span lang="EN-US">’ is an enum type.<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal"><span lang="EN-US">So how does one specify </span><span lang="EN-US" style="font-family:Consolas">cl::bits</span><span lang="EN-US"> with an external storage location if DataType is an enum? There is not much information in Command Line
Reference Manual. Note that I used <b>unsigned</b> above just like the excerpt from the manual says:<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US"><o:p> </o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande">The
</span><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">cl::bits</span><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande"> class is the class used to represent a list of command line options in the form of a bit vector. It is
also a templated class which can take up to three arguments:<o:p></o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">namespace</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier"> cl {<o:p></o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">template</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
<span style="color:#535353"><</span></span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">class</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#1370A6">DataType</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">,
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">class</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#1370A6">Storage</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
<span style="color:#535353">=</span> <span style="color:#7C1302">bool</span>,<o:p></o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">class</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#1370A6">ParserClass</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
<span style="color:#535353">=</span> parser<span style="color:#535353"><</span>DataType<span style="color:#535353">></span>
<span style="color:#535353">></span><o:p></o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#0D5F18">class</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">
</span><b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier-Bold;color:#1370A6">bits</span></b><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">;<o:p></o:p></span></p>
<p class="MsoNormal" style="text-autospace:none"><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">}<o:p></o:p></span></p>
<p class="MsoNormal"><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande">This class works the exact same as the
<u><span style="color:#BD6505">cl::list</span></u> class, except that the second argument must be of
</span><b><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande-Bold">type</span></b><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande">
</span><span lang="EN-US" style="font-size:13.0pt;font-family:Courier">unsigned</span><span lang="EN-US" style="font-size:14.0pt;font-family:LucidaGrande"> if external storage is used.</span><span lang="EN-US"><o:p></o:p></span></p>
</div>
</body>
</html>