https://gcc.gnu.org/bugzilla/show_bug.cgi?id=107172

--- Comment #26 from H.J. Lu <hjl.tools at gmail dot com> ---
(In reply to Uroš Bizjak from comment #24)
> (In reply to Hongtao.liu from comment #23)
> > looking at i386.c put_condition_code used by *setcc_qi, it looks like (EQ
> > (reg:CCCmode FLAG_REG) (const_int 0)) means get carry flag.
> > Not (LTU: (REG:CCCmode FLAGS_REG) (const_int 0)).
> > Now I got more confused.
> 
> CCCmode means that single flag is tested, it uses EQ and NE, so "c" and "nc"
> suffix is emitted. When CCmode is used, LTU/GEU operation on CCmode flags
> reg produces "b" and "nb" suffix, which decodes to exactly the same assembly
> as "c" and "nc" suffixes.
> 
> However, it looks that somewhere LTU/GEU is also generated with CCCmode
> flags reg, and some fixup was introduced to put_condition_code to "fix" this
> inconsistency. If LTU/GEU is valid only for CCmode, then the producers of
> invalid RTX should be fixed.

EQ and NE are only used to set FLAGS_REG in CCCmode from 2 integer operands.
LTU/GEU are only used to check FLAGS_REG against constant 0.  This is very
consistent.  simplify_const_relational_operation has

 /* We can't simplify MODE_CC values since we don't know what the
     actual comparison is.  */
  if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC)
    return 0;

In case of the comparison in CCCmode with constant op0 and op1, it should
let the backend perform the actual comparison.

Reply via email to