[HN Gopher] A few secure, random bytes without `pgcrypto`
___________________________________________________________________
A few secure, random bytes without `pgcrypto`
Author : surprisetalk
Score : 41 points
Date : 2024-09-24 21:49 UTC (4 days ago)
(HTM) web link (brandur.org)
(TXT) w3m dump (brandur.org)
| mhio wrote:
| gen_random_uuid() produces a v4 UUID.
|
| Taking the first 5 bytes of a v6 UUID (time) and last 5 (node)
| would be a bad random day.
| manwe150 wrote:
| Wait, is this blog actually about how to introduce a backdoor
| into your Postgres install by rolling your own very bad rng?
| fanf2 wrote:
| No, a v4 uuid comes from a good RNG. The blog post just said
| v6 by mistake when it meant v4.
| hinkley wrote:
| V6 is just a v4 rearranged to behave more like v7 for the
| purposes of b-tree insertion.
| dwattttt wrote:
| I believe V6 is a reordering of V1, not V4. V4 is random
| aside from the bits specifying version & variant, ~6/7
| bits.
| thadt wrote:
| Nah, mhio is saying that the blog post has a typo:
|
| > Postgres 13's gen_random_uuid() which generates a V6 UUID
| that's secure...
|
| gen_random_uuid gives you a version V4 UUID, not a V6 UUID
| (it's even in the code comments in the snipped included in
| the blog). I don't believe Postgres even _has_ a function to
| generate a V6 UUID - which, indeed, would be a bad idea to
| use as a source of randomness.
| hinkley wrote:
| I read this exact reply on this exact article two days ago.
|
| What is happening right now?
| tom_ wrote:
| Take the blue pill, press the back button, and pretend you
| never saw it.
|
| Or take the red pill, pull back the curtains of reality, and
| see the machinery behind:
| https://news.ycombinator.com/item?id=41197775
| hinkley wrote:
| I read this exact reply on this exact article two days ago.
|
| What is happening right now? Why is your comment marked four
| hours ago?
| davidfiala wrote:
| Exercise extreme caution.
|
| Having your security strategy rely on quirky behaviors of an
| implementation detail which might change is incredibly dangerous.
| hinkley wrote:
| UUID v6 isn't going to change. There's a reason we have seven
| of them now. And v8, which _would_ warrant your warning.
| poincaredisk wrote:
| UUIDv6 won't change, but what about gen_random_uuid()
| masklinn wrote:
| gen_random_uuid isn't going to change either, the entire
| point is to generate a secure uuid4. At most it'll get
| faster due to using platform-specific syscalls.
| creatonez wrote:
| There is widespread acceptance nowadays that randomized
| UUIDs must be generated from the system CSPRNG or something
| equivalent, and that any non-cryptographically secure
| method is a bug. Most library implementations across
| languages have converged on this in some way.
|
| That being said, the PostgreSQL documentation doesn't say
| anything in particular about the predictability of
| `gen_random_uuid`, so the behavior is unspecified. But it's
| worth noting the function has an explicit guard to raise an
| error if secure random is not available, so they were
| conscious of this possibility and did not attempt any
| misguided fallbacks.
|
| And unfortunately this requirement is not baked into the
| UUID spec either, which uses the word "should" instead of
| "must" when discussing CSPRNG usage.
| yunohn wrote:
| Not everything is a quirky implementation detail? It's
| important for us developers to not write pure glue code between
| others functions, but to also understand them and write our
| useful code that may extend others work.
| hinkley wrote:
| If you're shopping for a CSPRNG, one of the items that should be
| very high on your list is being able to call the setSeed function
| multiple times and have the inputs compose instead of clobber
| each other.
|
| You can send half-random input in and then send _more_ half-
| random input in until you're satisfied that the RNG has gotten a
| suitable amount of entropy. Do not chop, rearrange, hash, or bit
| shift the data trying to make it "stronger" the CSPRNG will do an
| infinitely better job of doing that for you. Just treat it like a
| Mr Fusion. Drop a can, a banana peel and the stale beer in and
| let it cook.
|
| I gave a similar speech to a team trying to initialize SSL
| sessions on an embedded machine. "But what if we XOR..." No.
| Stahp.
| ronsor wrote:
| Can you give some examples of CSPRNG implementations that allow
| this?
| andreareina wrote:
| The Linux rng allows writing to a file to effect this.
| hinkley wrote:
| The ones in Java did in the context of the original
| discussion. And cryptographic hash based PRNG should have the
| capability of doing so, it's an implementation detail whether
| you restart the data collection or append the data.
|
| Just poke in the setSeed function and see what it does.
| ynik wrote:
| > You can send half-random input in and then send more half-
| random input in until you're satisfied that the RNG has gotten
| a suitable amount of entropy.
|
| This does not actually work. If an attacker can observe output
| of the CSPRNG, and knows the initial state (when it did not yet
| have enough entropy), then piecemeal addition of entropy allows
| the attacker to bruteforce what the added entropy was. To be
| safe, you need to add a significant amount of entropy at once,
| without allowing the attacker to observe output from an
| intermediate state. But after you've done that, you won't ever
| need to add entropy again.
| beng-nl wrote:
| You're right, but I did not read GP to suggest otherwise.
|
| GP does not suggest using the output before enough entropy
| had been gathered, eg see 'until' in:
|
| > until you're satisfied that the RNG has gotten a suitable
| amount of entropy.
| hinkley wrote:
| Sibling already answered this. I don't know how you came to
| this conclusion.
| yunohn wrote:
| AFAIU the blog author is taking the correctly randomly
| generated UUID and just cutting out the timestamp portion.
|
| Why are you equating that to a hacky attempt to make less
| random data more random?
| hinkley wrote:
| Because it's essentially setSeed(getTimeMillis()). V6 and v7
| are sortable, that's why they exist. Which means like
| getTimeMillis() there are a finite number of starting points
| to try to guess the seed.
| yunohn wrote:
| This is v4.
| hinkley wrote:
| v6 is a transform of v1 UUIDs to behave like v7 keys with
| respect to database indexing - increasing over time. If
| it's a function of time, then it's still guessable by
| brute force.
|
| Another responder suggested that the mention of v6 UUIDs
| is an error. Maybe. But that's a truly bizarre typo to
| make. And they still haven't fixed it.
| yunohn wrote:
| But you could google Postgres UUID and confirm that they
| only provide v4? Instead of continuing a rant based on
| incorrect assumptions.
|
| https://www.postgresql.org/docs/current/functions-
| uuid.html
| amenhotep wrote:
| You seem to be saying that
|
| setSeed(0); setSeed(1); rand()
|
| and
|
| setSeed(1); rand()
|
| returning different values is not only a good idea but _is
| already a thing_. Am I wrong?
|
| This would confuse the hell out of me, what specifically has
| this behaviour?
| hinkley wrote:
| If you're trying to create a repeatable source of randomness
| for unit testing for example, you would create a new PRNG for
| each run, not try to recycle an existing instance. You're
| making assumptions about state that aren't supportable.
| Dylan16807 wrote:
| The behavior you are describing is not setting a seed. A
| seed should wipe out all existing state.
|
| Adding entropy is a very different operation.
___________________________________________________________________
(page generated 2024-09-28 23:00 UTC)