https://gcc.gnu.org/bugzilla/show_bug.cgi?id=116839
Bug ID: 116839
Summary: $fs:(%reg32) is used as memory operand for x32
Product: gcc
Version: 15.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: target
Assignee: unassigned at gcc dot gnu.org
Reporter: hjl.tools at gmail dot com
CC: lili.cui at intel dot com
Target Milestone: ---
Target: x86-64
[hjl@gnu-tgl-3 src]$ cat x.c
typedef long mpfr_prec_t;
typedef long mpfr_exp_t;
typedef struct {
mpfr_prec_t _mpfr_prec;
} __mpfr_struct;
typedef __mpfr_struct mpfr_t[1];
extern _Thread_local mpfr_exp_t __gmpfr_emax;
static _Thread_local mpfr_exp_t previous_emax;
static _Thread_local mpfr_t bound_emax;
extern const mpfr_t __gmpfr_const_log2_RNDD;
extern const mpfr_t __gmpfr_const_log2_RNDU;
typedef enum {
MPFR_RNDN=0,
MPFR_RNDZ,
MPFR_RNDU,
MPFR_RNDD,
MPFR_RNDA,
MPFR_RNDF,
MPFR_RNDNA=-1
} mpfr_rnd_t;
typedef __mpfr_struct *mpfr_ptr;
typedef const __mpfr_struct *mpfr_srcptr;
void mpfr_mul (mpfr_ptr, mpfr_srcptr, mpfr_rnd_t);
void
foo (void)
{
mpfr_exp_t saved_emax;
if (__gmpfr_emax != previous_emax)
{
saved_emax = __gmpfr_emax;
bound_emax->_mpfr_prec = 32;
mpfr_mul (bound_emax, saved_emax < 0 ?
__gmpfr_const_log2_RNDD : __gmpfr_const_log2_RNDU,
MPFR_RNDU);
previous_emax = saved_emax;
__gmpfr_emax = saved_emax;
}
}
[hjl@gnu-tgl-3 src]$ gcc -mtls-dialect=gnu2 -mx32 -O2 -fPIC -DPIC -S x.c
[hjl@gnu-tgl-3 src]$ grep cmp x.s
cmpl %fs:previous_emax@dtpoff(%eax), %r12d
[hjl@gnu-tgl-3 src]$
On x32, since address override works only on the (reg32) part in fs:(reg32),
we can't use it as memory operand.