Subject: Has gen_random_uuid() gotten much slower in v17?

From: David Mullineux <[email-masked]>
Date: Tue, 10 Sep 2024 14:58:03 +0100

I'm getting a bit concerned by the slow performance of generating uidds on
latest dev code versus older versions. Here I compare the time to generate
50k random uuids. Both son the same machine.
I must be missing something.

Any clues please ?

---

From: Peter Eisentraut <[email-masked]>
Date: Wed, 11 Sep 2024 11:40:16 +0200

On 10.09.24 15:58, David Mullineux wrote:
> I'm getting a bit concerned by the slow performance of generating uidds 
> on latest dev code versus older versions. Here I compare the time to 
> generate 50k random uuids. Both son the same machine.

Are you sure that the 18devel installation isn't compiled with 
assertions enabled?

The underlying code for gen_random_uuid() is virtually unchanged between 
PG14 and current.

---

From: David Mullineux <[email-masked]>
Date: Wed, 11 Sep 2024 11:47:41 +0100

Good idea. Thanks.    I did check. It's not enabled by default but just in
case I did another build. This time explicitly defining --disable-debug and
--disable-cassert. And I tested. Still slower than old versions.

This feels like a build configuration problem. Just can't put my finger on
it yet.

---

From: Frédéric Yhuel <[email-masked]>
Date: Wed, 20 Nov 2024 11:35:20 +0100

On 9/11/24 12:47, David Mullineux wrote:
> Good idea. Thanks.    I did check. It's not enabled by default but just 
> in case I did another build. This time explicitly defining --disable- 
> debug and --disable-cassert. And I tested. Still slower than old versions.
> 

4.5 seconds is very surprising.

on my machine:

postgres=# explain (analyze, costs off) select gen_random_uuid() from 
generate_series(1, 50000);
                                     QUERY PLAN 

----------------------------------------------------------------------------------
  Function Scan on generate_series (actual time=3.507..123.492 
rows=50000 loops=1)
  Planning Time: 0.031 ms
  Execution Time: 125.481 ms
(3 rows)

postgres=# select version();
                                            version 

----------------------------------------------------------------------------------------------
  PostgreSQL 18devel on x86_64-pc-linux-gnu, compiled by gcc (Debian 
12.2.0-14) 12.2.0, 64-bit

pg_config | grep CONFIGURE
CONFIGURE =  '--enable-cassert' '--enable-debug' '--with-python' 
'CFLAGS=-ggdb -Og -g3 -fno-omit-frame-pointer' '--prefix' 
'/postgres/pgenv/master'

> This feels like a build configuration problem. Just can't put my finger 
> on it yet.

Why not using a profiler to see what's going on?

---

From: Tom Lane <[email-masked]>
Date: Wed, 20 Nov 2024 10:46:06 -0500

> Why not using a profiler to see what's going on?

Yeah.  Also, are you building with openssl, or not?

			regards, tom lane

---

From: David Mullineux <[email-masked]>
Date: Wed, 20 Nov 2024 22:11:09 +0000

No, not at all!

---

From: Tom Lane <[email-masked]>
Date: Wed, 20 Nov 2024 17:26:29 -0500

[ please don't top-quote, it makes the conversation hard to follow ]

> No, not at all!

If you're not using openssl, then gen_random_uuid basically devolves
to a read of /dev/urandom.  Maybe you're using a different kernel
than before, and it has different properties around that?

			regards, tom lane

---

From: David Mullineux <[email-masked]>
Date: Tue, 26 Nov 2024 15:23:43 +0000

> than before, and it has different properties around that?

Just to say, thanks Tom. You were dead right. From the code in
pg_strong_random.c
it looks like each call will do an open("/dev/urandom")

And that cannot be fast.

Not sure why,but I guess there are good reasons to not keep a file
descriptor to that device open across calls ?

Thanks anyway