https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120524
Bug ID: 120524 Summary: `(__int128_var >> 127) & 1` is not optimized to ((unsigned __int128)__int128_var ) >> 127 in gimple level Product: gcc Version: 16.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: enhancement Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: pinskia at gcc dot gnu.org Target Milestone: --- Take: ``` __int128_t f(__int128_t a) { __int128_t t = a >> 127; return t & 1; } ``` This does not opimize to: ``` __int128_t f1(__int128_t a) { unsigned __int128 t = a; t >>= 127; return t; } ``` At the gimple level. This is because the match pattern only works with HOST_WIDE_INT rather than wi::wide_int: ``` /* Fold (X << C1) & C2 into (X << C1) & (C2 | ((1 << C1) - 1)) (X >> C1) & C2 into (X >> C1) & (C2 | ~((type) -1 >> C1)) if the new mask might be further optimized. */ (for shift (lshift rshift) (simplify (bit_and (convert?:s@4 (shift:s@5 (convert1?@3 @0) INTEGER_CST@1)) INTEGER_CST@2) (if (tree_nop_conversion_p (TREE_TYPE (@4), TREE_TYPE (@5)) && TYPE_PRECISION (type) <= HOST_BITS_PER_WIDE_INT && tree_fits_uhwi_p (@1) && tree_to_uhwi (@1) > 0 && tree_to_uhwi (@1) < TYPE_PRECISION (type)) ``` This pattern should be converted to use wi::wide_int instead of the current `unsigned HOST_WIDE_INT` .