Boost C++ Libraries: Ticket #12401: UB when sizeof(std::size_t) in floor_log2 https://svn.boost.org/trac10/ticket/12401 <p> The line </p> <pre class="wiki"> v |= v &gt;&gt; 32; // (*) </pre><p> in the following function, should fall in UB, when the sizeof(std::size_t) is 4, isn't it? </p> <pre class="wiki"> inline std::size_t floor_log2 (std::size_t v, integral_constant&lt;std::size_t, 64&gt;) { static const std::size_t MultiplyDeBruijnBitPosition[64] = { 63, 0, 58, 1, 59, 47, 53, 2, 60, 39, 48, 27, 54, 33, 42, 3, 61, 51, 37, 40, 49, 18, 28, 20, 55, 30, 34, 11, 43, 14, 22, 4, 62, 57, 46, 52, 38, 26, 32, 41, 50, 36, 17, 19, 29, 10, 13, 21, 56, 45, 25, 31, 35, 16, 9, 12, 44, 24, 15, 8, 23, 7, 6, 5}; v |= v &gt;&gt; 1; v |= v &gt;&gt; 2; v |= v &gt;&gt; 4; v |= v &gt;&gt; 8; v |= v &gt;&gt; 16; v |= v &gt;&gt; 32; // (*) return MultiplyDeBruijnBitPosition[((std::size_t)((v - (v &gt;&gt; 1))*0x07EDD5E59A4E28C2ULL)) &gt;&gt; 58]; } </pre> en-us Boost C++ Libraries /htdocs/site/boost.png https://svn.boost.org/trac10/ticket/12401 Trac 1.4.3 Ion Gaztañaga Fri, 19 Aug 2016 18:50:26 GMT status changed; resolution set https://svn.boost.org/trac10/ticket/12401#comment:1 https://svn.boost.org/trac10/ticket/12401#comment:1 <ul> <li><strong>status</strong> <span class="trac-field-old">new</span> → <span class="trac-field-new">closed</span> </li> <li><strong>resolution</strong> → <span class="trac-field-new">invalid</span> </li> </ul> <p> That function is only called if sizeof(std::size_t)*CHAR_BIT is 64: </p> <pre class="wiki"> inline std::size_t floor_log2 (std::size_t x) { const std::size_t Bits = sizeof(std::size_t)*CHAR_BIT; return floor_log2(x, integral_constant&lt;std::size_t, Bits&gt;()); } </pre><p> The 32 bit version uses only 16 bit shift: </p> <pre class="wiki"> inline std::size_t floor_log2 (std::size_t v, integral_constant&lt;std::size_t, 32&gt;) { static const int MultiplyDeBruijnBitPosition[32] = { 0, 9, 1, 10, 13, 21, 2, 29, 11, 14, 16, 18, 22, 25, 3, 30, 8, 12, 20, 28, 15, 17, 24, 7, 19, 27, 23, 6, 26, 5, 4, 31 }; v |= v &gt;&gt; 1; v |= v &gt;&gt; 2; v |= v &gt;&gt; 4; v |= v &gt;&gt; 8; v |= v &gt;&gt; 16; return MultiplyDeBruijnBitPosition[(std::size_t)(v * 0x07C4ACDDU) &gt;&gt; 27]; } </pre> Ticket