<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<!DOCTYPE bugzilla SYSTEM "https://bugs.webkit.org/page.cgi?id=bugzilla.dtd">

<bugzilla version="5.0.4.1"
          urlbase="https://bugs.webkit.org/"
          
          maintainer="admin@webkit.org"
>

    <bug>
          <bug_id>213383</bug_id>
          
          <creation_ts>2020-06-19 09:23:00 -0700</creation_ts>
          <short_desc>-Wsign-compare in isValidOptionSet</short_desc>
          <delta_ts>2020-06-22 14:44:07 -0700</delta_ts>
          <reporter_accessible>1</reporter_accessible>
          <cclist_accessible>1</cclist_accessible>
          <classification_id>1</classification_id>
          <classification>Unclassified</classification>
          <product>WebKit</product>
          <component>Web Template Framework</component>
          <version>WebKit Nightly Build</version>
          <rep_platform>PC</rep_platform>
          <op_sys>Linux</op_sys>
          <bug_status>RESOLVED</bug_status>
          <resolution>FIXED</resolution>
          
          
          <bug_file_loc></bug_file_loc>
          <status_whiteboard></status_whiteboard>
          <keywords>InRadar</keywords>
          <priority>P2</priority>
          <bug_severity>Minor</bug_severity>
          <target_milestone>---</target_milestone>
          
          
          <everconfirmed>1</everconfirmed>
          <reporter name="Michael Catanzaro">mcatanzaro</reporter>
          <assigned_to name="Michael Catanzaro">mcatanzaro</assigned_to>
          <cc>benjamin</cc>
    
    <cc>cdumez</cc>
    
    <cc>cmarcelo</cc>
    
    <cc>darin</cc>
    
    <cc>ddkilzer</cc>
    
    <cc>ews-watchlist</cc>
    
    <cc>mcatanzaro</cc>
    
    <cc>webkit-bug-importer</cc>
          

      

      

      

          <comment_sort_order>oldest_to_newest</comment_sort_order>  
          <long_desc isprivate="0" >
    <commentid>1664389</commentid>
    <comment_count>0</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 09:23:00 -0700</bug_when>
    <thetext>Since r263208 &quot;[IPC hardening] OptionSet&lt;&gt; values should be validated&quot;:

[4332/4574] Building CXX object Source...ources/UnifiedSource-50d0d8dd-14.cpp.o
In file included from /home/mcatanzaro/Projects/WebKit/Source/WebKit/Shared/glib/InputMethodState.h:31,
                 from /home/mcatanzaro/Projects/WebKit/Source/WebKit/Shared/glib/InputMethodState.cpp:27,
                 from DerivedSources/WebKit/unified-sources/UnifiedSource-50d0d8dd-14.cpp:1:
DerivedSources/ForwardingHeaders/wtf/OptionSet.h: In instantiation of ‘constexpr bool WTF::isValidOptionSet(WTF::OptionSet&lt;E&gt;) [with E = WebKit::InputMethodState::Hint]’:
/home/mcatanzaro/Projects/WebKit/Source/WebKit/Platform/IPC/ArgumentCoders.h:69:35:   required from ‘static bool IPC::ArgumentCoder&lt;WTF::OptionSet&lt;E&gt; &gt;::decode(IPC::Decoder&amp;, WTF::OptionSet&lt;E&gt;&amp;) [with T = WebKit::InputMethodState::Hint]’
/home/mcatanzaro/Projects/WebKit/Source/WebKit/Platform/IPC/ArgumentCoder.h:72:41:   required by substitution of ‘template&lt;class T&gt; static uint8_t IPC::UsesLegacyDecoder&lt;WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt; &gt;::checkArgumentCoder&lt;T&gt;(IPC::UsesLegacyDecoder&lt;WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt; &gt;::Helper&lt;bool (*)(IPC::Decoder&amp;, WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt;&amp;), (&amp; IPC::ArgumentCoder&lt;T&gt;::decode)&gt;*) [with T = WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt;]’
/home/mcatanzaro/Projects/WebKit/Source/WebKit/Platform/IPC/ArgumentCoder.h:76:85:   required from ‘constexpr const bool IPC::UsesLegacyDecoder&lt;WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt; &gt;::value’
/home/mcatanzaro/Projects/WebKit/Source/WebKit/Platform/IPC/Decoder.h:140:126:   required by substitution of ‘template&lt;class T, std::enable_if_t&lt;(((! std::is_enum&lt;_Tp&gt;::value) &amp;&amp; (! std::is_arithmetic&lt;_Tp&gt;::value)) &amp;&amp; (! IPC::UsesLegacyDecoder&lt;U&gt;::value))&gt;* &lt;anonymous&gt; &gt; bool IPC::Decoder::decode(T&amp;) [with T = WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt;; std::enable_if_t&lt;(((! std::is_enum&lt;_Tp&gt;::value) &amp;&amp; (! std::is_arithmetic&lt;_Tp&gt;::value)) &amp;&amp; (! IPC::UsesLegacyDecoder&lt;U&gt;::value))&gt;* &lt;anonymous&gt; = &lt;missing&gt;]’
/home/mcatanzaro/Projects/WebKit/Source/WebKit/Shared/glib/InputMethodState.cpp:117:36:   required from here
DerivedSources/ForwardingHeaders/wtf/OptionSet.h:257:52: warning: comparison of integer expressions of different signedness: ‘WTF::OptionSet&lt;WebKit::InputMethodState::Hint&gt;::StorageType’ {aka ‘unsigned int’} and ‘int’ [-Wsign-compare]
  257 |     return (optionSet.toRaw() | allValidBitsValue) == allValidBitsValue;
      |            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664394</commentid>
    <comment_count>1</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 09:35:11 -0700</bug_when>
    <thetext>Since this is a bitwise comparison, and we don&apos;t normally want to use signed types for bitwise comparisons, we probably want to cast allValidBitsValue on the right side of the expression to unsigned. I think that can be done using std::make_unsigned. Testing this....</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664415</commentid>
    <comment_count>2</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 10:46:26 -0700</bug_when>
    <thetext>So that does work, but I&apos;m going to try to mandate use of unsigned type instead. Using signed types with OptionSet is probably a mistake.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664429</commentid>
    <comment_count>3</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 11:21:11 -0700</bug_when>
    <thetext>(In reply to Michael Catanzaro from comment #2)
&gt; So that does work, but I&apos;m going to try to mandate use of unsigned type
&gt; instead. Using signed types with OptionSet is probably a mistake.

So that was a bad idea, because OptionSet goes out of its way to allow this:

using StorageType = std::make_unsigned_t&lt;std::underlying_type_t&lt;E&gt;&gt;;

I think isValidOptionSet should do the same. Let me try that.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664445</commentid>
    <comment_count>4</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 11:57:40 -0700</bug_when>
    <thetext>OK, I present two... options. ;)

Option #1: OptionSetValueChecker should match the OptionSet&apos;s StorageType, which is std::make_unsigned_t&lt;std::underlying_type_t&lt;E&gt;&gt;, instead of directly using std::underlying_type_t&lt;E&gt;:

diff --git a/Source/WTF/wtf/OptionSet.h b/Source/WTF/wtf/OptionSet.h
index de111b16b355..8450b1a240d9 100644
--- a/Source/WTF/wtf/OptionSet.h
+++ b/Source/WTF/wtf/OptionSet.h
@@ -253,8 +253,8 @@ private:
 template&lt;typename E&gt;
 WARN_UNUSED_RETURN constexpr bool isValidOptionSet(OptionSet&lt;E&gt; optionSet)
 {
-    auto allValidBitsValue = OptionSetValueChecker&lt;std::underlying_type_t&lt;E&gt;, typename EnumTraits&lt;E&gt;::values&gt;::allValidBits();
-    return (optionSet.toRaw() | allValidBitsValue) == allValidBitsValue;
+    auto allValidBitsValue = OptionSetValueChecker&lt;std::make_unsigned_t&lt;std::underlying_type_t&lt;E&gt;&gt;, typename EnumTraits&lt;E&gt;::values&gt;::allValidBits();
+    return (optionSet.toRaw() | allValidBitsValue) == std::underlying_type_t&lt;E&gt;(allValidBitsValue);
 }

That fixes the warning without making any changes in other files. I&apos;ll attach this patch for review.

Option #2: we could require the OptionSet to use an unsigned underlying value to call isValidOptionSet using std::enable_if. That would enforce unsigned underlying value only for OptionSets that are validated by isValidOptionSet. We only have to change the underlying type of WebKit::InputMethodState::Hint in Source/WebKit/Shared/glib/InputMethodState.h. I decided against making this my preferred option because valid OptionSets do not actually have to use unsigned underlying storage, so it would be a bit weird to require that to call isValidOptionSet, but this would be useful if we want to enforce this for types sent over IPC. (Do we want to enforce it for types sent over IPC?)

Option #3: would be to prohibit OptionSet from ever using signed underlying value, but that&apos;s going to require changing a lot of enums. Doesn&apos;t seem worth it, so I don&apos;t propose this.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664447</commentid>
    <comment_count>5</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 12:00:07 -0700</bug_when>
    <thetext>(In reply to Michael Catanzaro from comment #4)
&gt; +    return (optionSet.toRaw() | allValidBitsValue) ==
&gt; std::underlying_type_t&lt;E&gt;(allValidBitsValue);

That&apos;s a Ctrl+Z mistake, I&apos;ll attach a patch that actually works.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664448</commentid>
    <comment_count>6</comment_count>
      <attachid>402301</attachid>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 12:00:23 -0700</bug_when>
    <thetext>Created attachment 402301
Patch</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664451</commentid>
    <comment_count>7</comment_count>
    <who name="Michael Catanzaro">mcatanzaro</who>
    <bug_when>2020-06-19 12:06:48 -0700</bug_when>
    <thetext>(In reply to Michael Catanzaro from comment #4)
&gt; this would be useful if we want to enforce this
&gt; for types sent over IPC. (Do we want to enforce it for types sent over IPC?)

Maybe we do? r263208 ensured this for all types used in cross-platform code. If it&apos;s important, r- my patch and I&apos;ll upload a version that enforces this. The downside is that it would no longer be possible to call isValidOptionSet on valid OptionSets that use signed underlying storage, which would be weird.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664465</commentid>
    <comment_count>8</comment_count>
    <who name="EWS">ews-feeder</who>
    <bug_when>2020-06-19 12:52:27 -0700</bug_when>
    <thetext>Committed r263280: &lt;https://trac.webkit.org/changeset/263280&gt;

All reviewed patches have been landed. Closing bug and clearing flags on attachment 402301.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1664467</commentid>
    <comment_count>9</comment_count>
    <who name="Radar WebKit Bug Importer">webkit-bug-importer</who>
    <bug_when>2020-06-19 12:53:19 -0700</bug_when>
    <thetext>&lt;rdar://problem/64541629&gt;</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>1665185</commentid>
    <comment_count>10</comment_count>
    <who name="David Kilzer (:ddkilzer)">ddkilzer</who>
    <bug_when>2020-06-22 14:44:07 -0700</bug_when>
    <thetext>Thanks Michael!</thetext>
  </long_desc>
      
          <attachment
              isobsolete="0"
              ispatch="1"
              isprivate="0"
          >
            <attachid>402301</attachid>
            <date>2020-06-19 12:00:23 -0700</date>
            <delta_ts>2020-06-19 12:52:27 -0700</delta_ts>
            <desc>Patch</desc>
            <filename>bug-213383-20200619140022.patch</filename>
            <type>text/plain</type>
            <size>1562</size>
            <attacher name="Michael Catanzaro">mcatanzaro</attacher>
            
              <data encoding="base64">U3VidmVyc2lvbiBSZXZpc2lvbjogMjYzMjY4CmRpZmYgLS1naXQgYS9Tb3VyY2UvV1RGL0NoYW5n
ZUxvZyBiL1NvdXJjZS9XVEYvQ2hhbmdlTG9nCmluZGV4IGIxYjg1YzFjMGY0OTllNDdlZTc5OWU2
YTRkNTlhMzIwMDc5NTViNDEuLjFiNDFhYTc4ZDY3MGNlYTJjNzljOGFlZjM4NmI4ZmYyZWM4N2Zi
YTYgMTAwNjQ0Ci0tLSBhL1NvdXJjZS9XVEYvQ2hhbmdlTG9nCisrKyBiL1NvdXJjZS9XVEYvQ2hh
bmdlTG9nCkBAIC0xLDMgKzEsMTYgQEAKKzIwMjAtMDYtMTkgIE1pY2hhZWwgQ2F0YW56YXJvICA8
bWNhdGFuemFyb0Bnbm9tZS5vcmc+CisKKyAgICAgICAgLVdzaWduLWNvbXBhcmUgaW4gaXNWYWxp
ZE9wdGlvblNldAorICAgICAgICBodHRwczovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/
aWQ9MjEzMzgzCisKKyAgICAgICAgUmV2aWV3ZWQgYnkgTk9CT0RZIChPT1BTISkuCisKKyAgICAg
ICAgVGhlIE9wdGlvblNldCdzIFN0b3JhZ2VUeXBlIGlzIGFsd2F5cyB1bnNpZ25lZCwgZXZlbiBp
ZiB0aGUgZW51bSdzIHVuZGVybHlpbmcgdmFsdWUgaXMgbm90LgorICAgICAgICBNYXRjaCB0aGlz
IGluIGlzVmFsaWRPcHRpb25TZXQgdG8gYXZvaWQgLVdzaWduLWNvbXBhcmUgZHVyaW5nIHZhbGlk
aXR5IGNoZWNraW5nLgorCisgICAgICAgICogd3RmL09wdGlvblNldC5oOgorICAgICAgICAoV1RG
Ojppc1ZhbGlkT3B0aW9uU2V0KToKKwogMjAyMC0wNi0xOSAgTXlsZXMgQy4gTWF4ZmllbGQgIDxt
bWF4ZmllbGRAYXBwbGUuY29tPgogCiAgICAgICAgIFtDb2NvYV0gVW5pZnkgImZvbnQ6IiBDU1Mg
c2hvcnRoYW5kIHZhbHVlcyBiZXR3ZWVuIG1hY09TIGFuZCBpT1MgZmFtaWx5CmRpZmYgLS1naXQg
YS9Tb3VyY2UvV1RGL3d0Zi9PcHRpb25TZXQuaCBiL1NvdXJjZS9XVEYvd3RmL09wdGlvblNldC5o
CmluZGV4IGRlMTExYjE2YjM1NTI2ODJjMTFjYjJkMTc0N2QxZDMwN2QyNzhmOGUuLmQ5N2NjN2M0
MGMyZTcyMzhiM2RjYzc0NzVhNmE5ODEzYzE4MWZmNTkgMTAwNjQ0Ci0tLSBhL1NvdXJjZS9XVEYv
d3RmL09wdGlvblNldC5oCisrKyBiL1NvdXJjZS9XVEYvd3RmL09wdGlvblNldC5oCkBAIC0yNTMs
NyArMjUzLDcgQEAgcHJpdmF0ZToKIHRlbXBsYXRlPHR5cGVuYW1lIEU+CiBXQVJOX1VOVVNFRF9S
RVRVUk4gY29uc3RleHByIGJvb2wgaXNWYWxpZE9wdGlvblNldChPcHRpb25TZXQ8RT4gb3B0aW9u
U2V0KQogewotICAgIGF1dG8gYWxsVmFsaWRCaXRzVmFsdWUgPSBPcHRpb25TZXRWYWx1ZUNoZWNr
ZXI8c3RkOjp1bmRlcmx5aW5nX3R5cGVfdDxFPiwgdHlwZW5hbWUgRW51bVRyYWl0czxFPjo6dmFs
dWVzPjo6YWxsVmFsaWRCaXRzKCk7CisgICAgYXV0byBhbGxWYWxpZEJpdHNWYWx1ZSA9IE9wdGlv
blNldFZhbHVlQ2hlY2tlcjxzdGQ6Om1ha2VfdW5zaWduZWRfdDxzdGQ6OnVuZGVybHlpbmdfdHlw
ZV90PEU+PiwgdHlwZW5hbWUgRW51bVRyYWl0czxFPjo6dmFsdWVzPjo6YWxsVmFsaWRCaXRzKCk7
CiAgICAgcmV0dXJuIChvcHRpb25TZXQudG9SYXcoKSB8IGFsbFZhbGlkQml0c1ZhbHVlKSA9PSBh
bGxWYWxpZEJpdHNWYWx1ZTsKIH0KIAo=
</data>

          </attachment>
      

    </bug>

</bugzilla>