[PATCH v3 04/19] Add umul_ppmm to gmp-arch.hdoc

Adhemerval Zanella Netto adhemerval.zanella@linaro.org
Thu Nov 6 10:32:51 GMT 2025



On 03/11/25 03:31, Maciej W. Rozycki wrote:
> On Fri, 31 Oct 2025, Adhemerval Zanella wrote:
> 
>> Most of the architecture uses the generic implementation, which is
>> expanded from a macro, except for alpha, arm, hppa, x86, m68k, mips,
>> powerpc, and sparc.  I kept only x86 optimization, where there is no
>> easy way to emit mul{q}. For the rest, the compiler generates good
>> enough code.
> 
>  Hmm, this reference code works for me:
> 
> $ cat mulq.c
> typedef unsigned int __attribute__ ((mode (DI))) uint64_t;
> typedef unsigned int __attribute__ ((mode (TI))) uint128_t;
> 
> uint128_t
> mulq (uint64_t x, uint64_t y)
> {
>   return (uint128_t) x * (uint128_t) y;
> }
> $ x86_64-linux-gnu-gcc -O2 -S mulq.c -o x86_64-linux-gnu-mulq.s
> $ cat x86_64-linux-gnu-mulq.s
> 	.file	"mulq.c"
> 	.text
> 	.p2align 4
> 	.globl	mulq
> 	.type	mulq, @function
> mulq:
> .LFB0:
> 	.cfi_startproc
> 	movq	%rdi, %rax
> 	mulq	%rsi
> 	ret
> 	.cfi_endproc
> .LFE0:
> 	.size	mulq, .-mulq
> 	.ident	"GCC: (GNU) 11.0.0 20200919 (experimental)"
> 	.section	.note.GNU-stack,"",@progbits
> $ 
> 
> Is this not what you need?  It should work for any 64-bit platform that 
> has a widening multiply operation defined in the compiler backend, e.g. 
> for MIPS64:

You are right, I think I have missed something during my analysis.
I will refactor in terms of math_uint128.h as:

umul_ppmm_generic (mp_limb_t *w1, mp_limb_t *w0, mp_limb_t u, mp_limb_t v)
{
[...]
#if __MATH_INT128_BUILTIN_TYPE
  u128 r = (u128)u * (u128)v;
  *w1 = u128_high (r);
  *w0 = u128_low (r);
#else
  [...]
#endif
}

> 
> $ mips64-linux-gnu-gcc -O2 -S mulq.c -o mips64-linux-gnu-mulq.s
> $ cat mips64-linux-gnu-mulq.s
> 	.file	1 "mulq.c"
> 	.section .mdebug.abi64
> 	.previous
> 	.nan	legacy
> 	.module	fp=64
> 	.module	oddspreg
> 	.module	arch=mips3
> 	.abicalls
> 	.text
> 	.align	2
> 	.align	3
> 	.globl	mulq
> 	.set	nomips16
> 	.set	nomicromips
> 	.ent	mulq
> 	.type	mulq, @function
> mulq:
> 	.frame	$sp,0,$31		# vars= 0, regs= 0/0, args= 0, gp= 0
> 	.mask	0x00000000,0
> 	.fmask	0x00000000,0
> 	.set	noreorder
> 	.set	nomacro
> 	dmultu	$4,$5
> 	mflo	$3
> 	mfhi	$2
> 	jr	$31
> 	nop
> 
> 	.set	macro
> 	.set	reorder
> 	.end	mulq
> 	.size	mulq, .-mulq
> 	.ident	"GCC: (GNU) 12.0.1 20220404 (experimental)"
> 	.section	.note.GNU-stack,"",@progbits
> $
> 
>   Maciej



More information about the Libc-alpha mailing list