101

I see a lot of sites use GUIDs for password resets, unsubscribe requests and other forms of unique identification.

Presumably they are appealing because they are easy to generate, unique, non-sequential and seem random.

But are they safe enough for these purposes?

It seems to me that given a GUID, predicting subsequent GUIDs may be possible since (as far as I know) they're not intended to be cryptographically secure...or are they?

Note:

  • I'm not talking about sites that use a random blob of gobbledygook encoded in base64.
  • I'm talking about sites like this that appear to be using a raw guid:
    http://example.com/forgotPassword/?id=b4684ce3-ca5b-477f-8f4d-e05884a83d3c
7
  • That depends if you can create/predict what's gonna be the next GUID in use.
    – Marcin
    Commented Nov 30, 2010 at 15:59
  • 2
    It all depends on exactly what you mean by GUID and how it was generated. Looking at a URL it may seem that it is in UUID format, and you may guess it was generated by Microsoft's insecure GUID algorithm, and thus it would not be suitable for any use like what you propose. But it might have been generated using a good cryptographically secure pseudo-random source like /dev/random in Linux, in which case it would be just fine.
    – nealmcb
    Commented Nov 30, 2010 at 20:59
  • @nealmcb: sure--this isn't a direct criticism of any particular site. Instead, I'm trying to confirm my suspicion that such a practice (secure ID via guid) is probably not good. Consensus seems to be that GUIDs are predictable (though non-trivial to predict), and more secure means should be used. Commented Nov 30, 2010 at 21:35
  • 2
    @nealmcb, it isnt just MS' implementation, its the standard for GUIDs.
    – AviD
    Commented Dec 1, 2010 at 21:08
  • 1
    @avid We agree that nothing in the RFC specifies that even type 4 "random" UUIDS are cryptographically secure. My only point was that you could use a good implementation of the RFC for security purposes. E.g. on a modern Linux box with /dev/random, the libuuid library (and uuidgen program) will by default generate very good, unpredictable UUIDs. kernel.org/doc/man-pages/online/pages/man4/random.4.html But it is surely better for security software to directly use an API that is designed specifically to provide crypto randomness, since someone may carelessly port the code.
    – nealmcb
    Commented Dec 2, 2010 at 3:10

6 Answers 6

47

Are they safe enough for the purposes you described? In my opinion, generally yes. Are they safe enough in applications where security is a significant concern? No. They're generated using a non-random algorithm, so they are not in any way cryptographically random or secure.

So for an unsubscribe or subscription verification function, I really don't see a security issue. To identify a user of an online banking application on the other hand, (or really probably even a password reset function of a site where identity is valuable) GUIDs are definitely inadequate.

For more information, you might want to check out section 6 (Security Considerations) of the RFC 4122 for GUIDs (or Universally Unique Identifiers).

5
  • 6
    The purpose he described is exactly a password reset function. While it is clear that you are stating that GUID is not acceptable for any security use, your first sentence contradicts that.
    – AviD
    Commented Nov 30, 2010 at 16:38
  • 2
    And I'd agree that it's acceptable for a password reset function on most sites. Not for banking sites, or sites where assuming another user's identity would be particularly valuable, but most sites simply don't present a valuable target for this sort of attack, or a high enough volume of password-reset requests for an attack of this nature to work in the first place.
    – Xander
    Commented Nov 30, 2010 at 16:49
  • 1
    Password reset at most organisations I have worked was definitely considered at a lower security level than authentication for transactional sites etc. Yes, it is a vector for attack, however the limitations imposed (time, knowledge of secret information etc) and the cost reductions made in simplifying password self reset (any reduction in helpdesk calls saves money) are generally considered enough of a driver.
    – Rory Alsop
    Commented Nov 30, 2010 at 18:26
  • 3
    Hmm, I guess that's true, for low-value sites GUID may be good enough. But really, as @massimo mentions in his answer, why bother? Cryptorandom numbers are not costly, neither in dev time or processing time.
    – AviD
    Commented Nov 30, 2010 at 19:56
  • 3
    Point taken. I'd agree that even if they're suitable for the purpose at hand, they're still not the best option from a security perspective.
    – Xander
    Commented Nov 30, 2010 at 21:45
68

The UUID specification details several "versions" which are methods for generating the UUID. Most are aimed at ensuring uniqueness (that's the main point of UUID) by using, e.g., the current date. This is efficient but means that while the generated UUID are unique, they are also predictable, which makes them inadequate for some security usages.

The "version 4" UUID generation method (in section 4.4), however, is supposed to use a cryptographically strong random number generator. 6 of the 128 bits are fixed to a conventional value (to indicate that this is a version 4 UUID, namely), so this leaves 122 bits from the RNG.

If the underlying RNG is secure (e.g. /dev/urandom on a Linux/MacOS/*BSD system, or CryptGenRandom() on Windows) then given many generated UUID, an attacker is not supposed to be able to predict the next one with success probability higher than 2-122, which is adequately small for most purposes, including launch codes for nuclear missiles.

122 random bits ensure uniqueness with high probability. If you generate many version 4 UUID and accumulate them, you may expect to encounter your first collision after about 261 UUID -- that's about 2 billions of billions; simply storing that number of UUID would use more than 30 millions of terabytes. If you consider "only" 1012 such UUID (one thousand of billions, storable over 16 terabytes), then risks of having two identical UUID among these are about 9.4*10-14, i.e. about 700 thousands times less probable than winning millions of dollars at the lottery.

Therefore, UUID are appropriate for security purposes if (and only if) they are "version 4" UUID generated with a secure RNG.

2
  • It says"The version 4 UUID is meant for generating UUIDs from truly-random or pseudo-random numbers." (FWIW) ...
    – rogerdpack
    Commented Mar 6, 2020 at 1:28
  • UUID generators can still produce predictable UUID sequences even when using CSPRNG. The spec does not require them to generate entirely new random bytes for each successive UUID. Also the spec explicitly says UUID should not be used for auth tokens.
    – jchook
    Commented Oct 16, 2021 at 20:22
6

They are secure on Windows 2000 or newer. Your vulnerability & risk depends on how the GUID is generated. Windows 2000 or newer uses version 4 of the GUID which is cryptographically secure.

For more information see this MSDN link and this stack overflow question. (Thanks to Jordan Rieger in the comments)

5
  • 4
    Why complicate things by encrypting a not-so-random number? Better and simpler to just generate a truly unpredictable random number. That is easy with /dev/random or /dev/urandom on Linux. We just need a simple specific recipe here for other platforms.
    – nealmcb
    Commented Jan 30, 2011 at 16:27
  • @nealmcb sometimes it's not possible to define the randomness of this number (e.g. the ID comes from a backend system from 3rd party). May not apply the OP Commented Feb 17, 2017 at 18:45
  • 1
    According to msdn.microsoft.com/en-us/library/…, since Windows 2000 back in 1999, "the random bits for all version 4 GUIDs built in Windows are obtained via the Windows CryptGenRandom cryptographic API or the equivalent, the same source that is used for generation of cryptographic keys". So I'd say you could call them cryptographically secure -- at least to the extent of the 122 bits of entropy they provide. Commented May 28, 2018 at 19:45
  • @JordanRieger Thanks - updated. I tried to find the containing document "home", but was hindered by MSDN navigation. Is this product documentation for ".NET" "Windows", or something else? Commented May 28, 2018 at 21:25
  • 1
    @CHICoder007 MSDN navigation seems broken. Following the section numbers backward as far as possible leads to msdn.microsoft.com/en-us/library/…, a dead end. It's definitely Windows SDK documentation of some kind. I found it by stumbling on this blog post: joakim.uddholm.com/posts/predicting-net-guidnewguid.html (the doc page may have been updated since then as the blog references end note 9 when it's actually end note 11.) This also matches a recent debug/step-through by Will Dean in stackoverflow.com/a/35384818/284704. Commented May 29, 2018 at 0:26
3

If you're using a common development language creating a one shot generator of unique random numbers using a proper crypto function is not so difficult (we're talking about 10 lines of code that are available as samples in the most common languages simply using Google) and so using a simple new guid it's basically laziness from developer point of view.

In the scenario described they are "secure enough", if the Guid passed in the forgot password function has some basic features:

1) It's really a one shot value that has no relationship with the user id, so, once the password has been reset, cannot be used anymore

2) It has a defined window of time for its validity (you can reset password in the next 30 minutes or something like that)

If using the same Guid you can reset the password more than once or guess the guid and reset password of users that did not ask for a password reset or, like Avid describe in the comment, try to get access to reset password using some kind of replay attach then it's the application design that's faulty and using or not using a Guid is not the real problem.

So if you're not dealing with very sensitive information then maybe a guid could work, but why do not make things in a proper way the first time and use a proper crypto api to generate a secure random string?

Regards Massimo

3
  • I agree with the first part of your answer generating crypto-random numbers is extremely easy (and should take substantially less than 10 LoC...). However, in the scenario described they are not secure enough, since there is no guarantee that the password is reset immediately: There is usually a non-trivial window of validity.
    – AviD
    Commented Nov 30, 2010 at 16:40
  • 3
    For example, consider the following: often this scheme is used to send a link to the user's preregistered email, which will allow direct access to reset the user's password. As an attacker, I would generate enough of these links/GUIDs till I could semi-reliably calculate the next batch, then ask to send the link to my victim (essentially having the user ask for a password reset). Then I would not care about access to the user's email, since I could just guess the GUID/link.
    – AviD
    Commented Nov 30, 2010 at 16:44
  • 2
    @Rory, I was talking about the inherent guessability of GUIDs (given enough prior data), not replay attacks...
    – AviD
    Commented Nov 30, 2010 at 19:55
1

According to Raymond Chen at Microsoft, even version 4 GUIDs used in Windows since 2000 are not cryptographically secure. They use the basic random number generator, which can allow someone to predict past and future GUIDs if they know the state of the generator. Granted, this would only be relevant to a security-sensitive application. It's important to know that standard Guid.NewGuid() values are only guaranteed to be "most certainly" unique, not secure.

0

Fake "GUID"s, which are not generated by any GUID generation algorithm, but which instead are simply 128 bits (16 bytes) generated by a cryptographically secure PRNG, and which are merely represented using conventional GUID hex-with-hyphens encoding, are mostly safe for one-time tokens.

You do run into the birthday problem, however, since the existence of a collision is around 2^-64 for 128-bit tokens.

Better to use 256-bit or 512-bit tokens, where the existence of a collision is around 2^-128 or 2^-256.

2
  • This is simply not true, at least not in general. If you are building on @Thomas's answer, then it starts to look more plausible but is still less accurate than his. Commented Oct 7, 2011 at 17:38
  • It should be clearer now.
    – yfeldblum
    Commented Oct 7, 2011 at 17:50

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .