On Wed, May 13, 2026 at 08:05:12PM +0530, jeevitha wrote:
> Gentle Ping!
>
> Thanks & Regards
> Jeevitha
>
> On 14/04/26 5:04 pm, jeevitha wrote:
> > Hi All,
> >
> > The following patch has been bootstrapped and regtested on
> > powerpc64le-linux.
> >
> > Changes from V1:
> > * Added new test pr106895-2.c.
> >
> > PTImode is used to generate even/odd register pairs for 128-bit values.
> > When PTImode is specified via a type attribute, compilation fails
> > because no internal type exists to represent this mode.
> >
> > Introduce signed and unsigned PTImode internal builtin types to handle
> > PTImode. These __pti_internal types are not documented, as they are not
> > intended for direct user use.
> >
> > 2026-04-14 Jeevitha Palanisamy <[email protected]>
Some minor comments. It is ok to commit if you make the changes and do
a bootstrap on both 32-bit and 64-bit systems to ensure there are no
other regressions with the changes.:
> > gcc/
> > PR target/106895
> > * config/rs6000/rs6000.h (enum rs6000_builtin_type_index): Add
> > RS6000_BTI_INTPTI and RS6000_BTI_UINTPTI.
> > (intPTI_type_internal_node, uintPTI_type_internal_node): New
> > PTImode type macros.
> > * config/rs6000/rs6000-builtin.cc (rs6000_init_builtins): Register
> > signed and unsigned PTImode internal builtin types.
> > * config/rs6000/sync.md (trunctipti2): New splitter.
> > (extendptiti2): Likewise.
> > (zero_extendptiti2): Likewise.
> >
> > gcc/testsuite/
> > PR target/106895
> > * gcc.target/powerpc/pr106895-1.c: New test.
> > * gcc.target/powerpc/pr106895-2.c: New test.
> >
> > diff --git a/gcc/config/rs6000/rs6000-builtin.cc
> > b/gcc/config/rs6000/rs6000-builtin.cc
> > index bbf60de3b1b..8561cd67f53 100644
> > --- a/gcc/config/rs6000/rs6000-builtin.cc
> > +++ b/gcc/config/rs6000/rs6000-builtin.cc
> > @@ -756,6 +756,19 @@ rs6000_init_builtins (void)
> > else
> > ieee128_float_type_node = NULL_TREE;
> >
> > + /* PTImode to get even/odd register pairs. */
> > + intPTI_type_internal_node = make_signed_type (GET_MODE_BITSIZE
> > (PTImode));
> > + SET_TYPE_MODE (intPTI_type_internal_node, PTImode);
> > + t = build_qualified_type (intPTI_type_internal_node, TYPE_QUAL_CONST);
> > + lang_hooks.types.register_builtin_type (intPTI_type_internal_node,
> > + "__pti_internal");
> > +
> > + uintPTI_type_internal_node = make_unsigned_type (GET_MODE_BITSIZE
> > (PTImode));
> > + SET_TYPE_MODE (uintPTI_type_internal_node, PTImode);
> > + t = build_qualified_type (uintPTI_type_internal_node, TYPE_QUAL_CONST);
> > + lang_hooks.types.register_builtin_type (uintPTI_type_internal_node,
> > + "__upti_internal");
> > +
> > /* Vector pair and vector quad support. */
> > vector_pair_type_node = make_node (OPAQUE_TYPE);
> > SET_TYPE_MODE (vector_pair_type_node, OOmode);
Given 128-bit integer types are only implemented on 64-bit systemss, I
think adding these two types should be under a TARGET_POWERPC64 test.
> > diff --git a/gcc/config/rs6000/rs6000.h b/gcc/config/rs6000/rs6000.h
> > index 2b90694cef1..d85f71aa65d 100644
> > --- a/gcc/config/rs6000/rs6000.h
> > +++ b/gcc/config/rs6000/rs6000.h
> > @@ -2285,6 +2285,8 @@ enum rs6000_builtin_type_index
> > RS6000_BTI_ptr_vector_quad,
> > RS6000_BTI_ptr_long_long,
> > RS6000_BTI_ptr_long_long_unsigned,
> > + RS6000_BTI_INTPTI,
> > + RS6000_BTI_UINTPTI,
> > RS6000_BTI_MAX
> > };
> >
> > @@ -2329,6 +2331,8 @@ enum rs6000_builtin_type_index
> > #define uintDI_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_UINTDI])
> > #define intTI_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_INTTI])
> > #define uintTI_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_UINTTI])
> > +#define intPTI_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_INTPTI])
> > +#define uintPTI_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_UINTPTI])
> > #define float_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_float])
> > #define double_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_double])
> > #define long_double_type_internal_node
> > (rs6000_builtin_types[RS6000_BTI_long_double])
> > diff --git a/gcc/config/rs6000/sync.md b/gcc/config/rs6000/sync.md
> > index 7087daf7e4c..4e392584bbc 100644
> > --- a/gcc/config/rs6000/sync.md
> > +++ b/gcc/config/rs6000/sync.md
> > @@ -198,6 +198,54 @@
> > DONE;
> > })
> >
> > +;; PTI and TI are both 128-bit modes; the following conversions are
> > +;; register-class changes only, no actual truncation, sign or zero
> > +;; extension occurs.
> > +(define_insn_and_split "trunctipti2"
> > + [(set (match_operand:PTI 0 "register_operand" "=r")
> > + (truncate:PTI (match_operand:TI 1 "register_operand" "r")))]
> > + ""
> > + "#"
> > + "&& reload_completed"
> > + [(set (match_dup 2) (match_dup 4))
> > + (set (match_dup 3) (match_dup 5))]
> > +{
> > + operands[2] = gen_lowpart (DImode, operands[0]);
> > + operands[3] = gen_highpart (DImode, operands[0]);
> > + operands[4] = gen_lowpart (DImode, operands[1]);
> > + operands[5] = gen_highpart (DImode, operands[1]);
> > +})
You should set the length attribute because the conditional jump
generation needs to know how big each insn is, so that if necessary, it
can reverse the test and generate a jump over an unconditional jump.
Also, we should limit this to 64-bit systems.
Now, one other thing that in theory is helpful is to have an
alternative where the same register is used. This dead copy is
eliminated, but it can help if the register allocator uses the same
register. Something like:
;; PTI and TI are both 128-bit modes; the following conversions are
;; register-class changes only, no actual truncation, sign or zero
;; extension occurs. If the register allocator uses the same input
;; and output register, the useless copies will be deleted.
(define_insn_and_split "trunctipti2"
[(set (match_operand:PTI 0 "register_operand" "=r,r")
(truncate:PTI (match_operand:TI 1 "register_operand" "0,r")))]
"TARGET_POWERPC64"
"#"
"&& reload_completed"
[(set (match_dup 2) (match_dup 4))
(set (match_dup 3) (match_dup 5))]
{
operands[2] = gen_lowpart (DImode, operands[0]);
operands[3] = gen_highpart (DImode, operands[0]);
operands[4] = gen_lowpart (DImode, operands[1]);
operands[5] = gen_highpart (DImode, operands[1]);
}
[(set_attr "length" "0,8")])
> > +(define_insn_and_split "extendptiti2"
> > + [(set (match_operand:TI 0 "register_operand" "=r")
> > + (sign_extend:TI (match_operand:PTI 1 "register_operand" "r")))]
> > + ""
> > + "#"
> > + "&& reload_completed"
> > + [(set (match_dup 2) (match_dup 4))
> > + (set (match_dup 3) (match_dup 5))]
> > +{
> > + operands[2] = gen_lowpart (DImode, operands[0]);
> > + operands[3] = gen_highpart (DImode, operands[0]);
> > + operands[4] = gen_lowpart (DImode, operands[1]);
> > + operands[5] = gen_highpart (DImode, operands[1]);
> > +})
Similar changes here.
> > +(define_insn_and_split "zero_extendptiti2"
> > + [(set (match_operand:TI 0 "register_operand" "=r")
> > + (zero_extend:TI (match_operand:PTI 1 "register_operand" "r")))]
> > + ""
> > + "#"
> > + "&& reload_completed"
> > + [(set (match_dup 2) (match_dup 4))
> > + (set (match_dup 3) (match_dup 5))]
> > +{
> > + operands[2] = gen_lowpart (DImode, operands[0]);
> > + operands[3] = gen_highpart (DImode, operands[0]);
> > + operands[4] = gen_lowpart (DImode, operands[1]);
> > + operands[5] = gen_highpart (DImode, operands[1]);
> > +})
> > +
> > ;; If TARGET_PREFIXED, always use pstq rather than stq.
> > (define_insn "store_quadpti"
> > [(set (match_operand:PTI 0 "quad_memory_operand" "=wQ")
And here.
--
Michael Meissner, IBM
PO Box 98, Ayer, Massachusetts, USA, 01432
email: [email protected]