How does C# generate GUIDs?
Asked Answered
R

9

51

How are GUIDs generated in C#?

Reece answered 11/12, 2009 at 14:0 Comment(5)
Voting to close as a duplicate of How are .NET 4 GUIDs generated?. I guess it's not a perfect duplicate in principle (especially since now .NET Core exists, and it's unclear whether the answer at the dupe is true of .NET Core on non-Windows OSes), but currently this question doesn't have an answer that even comes close to being correct and the linked dupe does.Kinzer
I agree that this doesn't have an answer that comes close to being correct. Anyone coming here for actually useful information please see https://mcmap.net/q/22128/-how-are-net-4-guids-generatedOomph
@MarkAmery Neither is a duplicate. This question was asked 6 months earlier than the one you referenced and the other is specific to version 4. How are .NET 4 GUIDs generated? has solid answers, but one should really consider RFC 4122 to get the full picture.Augsburg
@Augsburg "This question was asked 6 months earlier" - true, but unimportant. It's perfectly legit to close an older question as a duplicate of a newer one. We should primarily be considering which is the more useful question for a searcher to end up at when deciding closure direction; age doesn't matter.Kinzer
@MarkAmery While I found your response reasonable, I wanted to exercise a proper amount of skepticism and found this answer in agreement with yours as well as articles in the Help section that point to the same sentiment. On that note, I'll also vote this as a dupe. ;)Augsburg
C
11

Original question:

How the Guid is generating it's identifier?? How will be it's output if I use the following code Guid g = Guid.NewGuid();

Whether the output will be the combination of numbers and lettters or the numbers alone will be there???

A .Net System.Guid is just a 128-bit integer (16 bytes). Numbers and letters have nothing to do with it. You can use the ToString() method to see various "human-readable" versions of a Guid, which include numbers 0-9 and letters A-F (representing hex values), but that's all up to you how you want to output it.

Cerelly answered 11/12, 2009 at 14:4 Comment(3)
This answer is wrong because it answers to "What is GUID?" but the real question is "How does C# generate GUIDs?". Therefore the answer provided by @Imaginable is the right answer.Goya
@OgnyanDimitrov - The original question was pretty ambiguous because of broken English. It sounded like the request had to do with the string representation of the GUID. You can look at the history of the question. It's arguable that the meaning of the original question was changed, given the edits that were made and the fact that this answer was accepted by the asker. I'll add the original question to my answer, in case that's the question someone is coming to this page with.Cerelly
Please, do not be offended. I do not write this to blame or ridicule. You can edit your answer now not because of anything else but to improve the quality of it even though the question was vague in the first place. The next guy that comes across from a search result will get the better answer. I am sure that you are experience and knowledgeable and I did not mean to belittle your answer.Goya
I
65

There's a really good article on Raymond Chen's blog that describes how GUIDs are generated, and in particular why a substring of a guid is not guaranteed to be unique.

Basically, a a GUID is generated using a combination of:

  • The MAC address of the machine used to generate the GUID (so GUIDs generated on different machines are unique unless MAC addresses are re-used)
  • Timestamp (so GUIDs generated at different times on the same machine are unique)
  • Extra "emergency uniquifier bits" (these are used to ensure that GUIDs generated at nearly exactly the same time on the same machine are unique)
  • An identifier for the algorithm (so that GUIDs generated with a different algorithm are unique)

However, this is only 1 particular algorithm used for generating GUIDs (although I believe it's the one used by the .NET framework), and is not the one used by the .NET framework.

Imaginable answered 11/12, 2009 at 14:43 Comment(2)
.NET uses Windows' algorithm which creates a random number (version 4 GUID) starting with Windows 2000: https://mcmap.net/q/22128/-how-are-net-4-guids-generatedMytilene
-1; this answer basically torpedoes its entire premise with the link at the end of the final sentence and admits to not being an answer to the question asked.Kinzer
A
14

The algorithm is documented here as Globally unique identifier

Aubry answered 11/12, 2009 at 14:4 Comment(1)
That article discusses several different algorithms for generating GUIDs. Which one is the one .NET actually uses?Uchish
C
11

Original question:

How the Guid is generating it's identifier?? How will be it's output if I use the following code Guid g = Guid.NewGuid();

Whether the output will be the combination of numbers and lettters or the numbers alone will be there???

A .Net System.Guid is just a 128-bit integer (16 bytes). Numbers and letters have nothing to do with it. You can use the ToString() method to see various "human-readable" versions of a Guid, which include numbers 0-9 and letters A-F (representing hex values), but that's all up to you how you want to output it.

Cerelly answered 11/12, 2009 at 14:4 Comment(3)
This answer is wrong because it answers to "What is GUID?" but the real question is "How does C# generate GUIDs?". Therefore the answer provided by @Imaginable is the right answer.Goya
@OgnyanDimitrov - The original question was pretty ambiguous because of broken English. It sounded like the request had to do with the string representation of the GUID. You can look at the history of the question. It's arguable that the meaning of the original question was changed, given the edits that were made and the fact that this answer was accepted by the asker. I'll add the original question to my answer, in case that's the question someone is coming to this page with.Cerelly
Please, do not be offended. I do not write this to blame or ridicule. You can edit your answer now not because of anything else but to improve the quality of it even though the question was vague in the first place. The next guy that comes across from a search result will get the better answer. I am sure that you are experience and knowledgeable and I did not mean to belittle your answer.Goya
M
3

It depends. For .NET Core in Unix GUIDs, are generated by creating a random number of 128 bits and and doing a couple bit wise operations. In .NET Core for Windows and .NET framework it makes a remote procedure call to the Windows function UuidCreate (so it's completely up to your Windows version on how they are generated). For Unix and recent versions of Windows, you'll notice that there is one hex digit that is always a 4. That is because it the version number for the Uuid 4, which just means they are generated with random bytes. GUIDs used to be generated with things like the timestamp and MAC address, but that became an attack vector because it told end users information about the system and helped them predict future GUIDs easier.

Marleen answered 1/11, 2019 at 6:17 Comment(1)
This is one of the best answers I've found all day.Galarza
B
2

There are also other forms of GUID besides "random 16 bytes", as mentioned in the RFC. Some Microsoft products (SQL Server for instance) can optionally generate these "sequential GUIDs" which are based on a combination of "MAC address of first network card in the system + ever-increasing counter based on system time".

These "sequential GUIDs" have the nice property of always appending new records to the "end" of a database table when used as a database primary key with a clustered index. This helps prevent database index fragmentation and page splits.

If random GUIDs are used as database primary keys with clustered indexes, new records will be inserted randomly in the "middle" of a table from a physical allocation standpoint, which leads to index fragmentation and partially-full database pages over time.

Using sequential GUIDs still allows you to generate GUIDs independently on multiple systems and be confident there will not be any collisions (a property that you do not get using sequential integers as primary keys without allocating "ranges" or different seeds and increments to each system, which is an administrative nightmare in large distributed applications).

Bufflehead answered 11/12, 2009 at 14:33 Comment(1)
The question asked about GUID generation in C#, and this answer is irrelevant to that; -1.Kinzer
C
0

Details on Wikipedia and MSDN.

In short, a GUID is a random 128-bit integer, but we format them using hex digits so that they are easily readable (this is the 8-4-4-4-12 format that you see). As far as how its generated, see the linked Wikipedia article.

Cobweb answered 11/12, 2009 at 14:5 Comment(1)
-1; per the Wikipedia article you link to, there are 5 different standardised UUID-generation algorithms. "see the linked Wikipedia article" thus doesn't answer the question of how C# in particular generates UUIDs.Kinzer
D
0

The bits of the GUID break down like this:

  • 60 bits of timestamp
  • 48 bits of computer identifier
  • 14 bits of uniquifier
  • 6 bits are fixed

Total of 128 bits.

Daubery answered 18/7, 2017 at 8:8 Comment(1)
-1; this answer is not true of GUIDs generated with C#'s Guid.NewGuid on Windows, as noted in https://mcmap.net/q/22128/-how-are-net-4-guids-generated. Indeed, there are good privacy reasons for all languages/OSes/frameworks to avoid the GUID-generation algorithm you describe here (or at least not use it as a default), as the convict David L. Smith could explain to you.Kinzer
K
0

We can check this directly against generated GUIDs. I'd prefer some source documents, but TBH the Wikipedia rundown is pretty good. The first relevant section is on GUID Variants. Summary: in order to determine the GUID type, we'll have to look at the variant and possibly a version.

Which variant (& version) are .NET-generated GUIDs?

Variant is indicated by the initial bits of the 9th octet. It is done by "pinning" the initial bits to 0, 10, 110 or 111. Using

string show(Guid g) => $"{g}: fam {Convert.ToString(g.ToByteArray()[8], 2)}";
show(Guid.NewGuid())

we might get "1b579ecd-b72c-4550-b10b-f8dd41699ac1: fam 10110001". The family is pinned to 10, OSF DCE UUID or variant 2. This variant defines a version, held in the more significant "nibble" of the 7th octet.

BUT, there is a complicating factor: endianness in encoding. These MS-based sections are stored in a little-endian format. Let's take a look: with another quick method

void SeeOrder(Guid g) => Console.WriteLine($"{g}\n{g:N}\n{string.Join("", g.ToByteArray().Select(b => $"{b:x2}"))}"); 

we'll see a result like

dd3f9bdf-ba47-4411-84c8-6cfcc5d39bb5
dd3f9bdfba47441184c86cfcc5d39bb5
df9b3fdd47ba114484c86cfcc5d39bb5

The first three groups are transposed, because each is a complete integer (two for time, one reserved; 32, 16 and 16 bits respectively). The last two groups are not, because the last 8 octets are a "string": 1 reserved octet (where the "family" is represented) and 7 "node" octets.

So the 7th version octet is actually encoded as the 8th (index 7). Expanding show to highlight the version:

string show(Guid g) => $"{g}: fam {Convert.ToString(g.ToByteArray()[8], 2)}, ver {g.ToByteArray()[7].ToString("x")}";

We'll get "154573de-d420-433b-bb25-aff50590038b: fam 10111011, ver 43". The nibble in question is the 4, thus version 4: pseudo-random generation.

As you can see in the above examples, the variant 2 version shows up as the first hex char of the 3rd group. You'll notice in .NET GUIDs, it will always be 4. After reading this you'll never not look for that 4.

You're welcome.

Kinch answered 18/8, 2023 at 21:58 Comment(0)
D
-2

A Guid is a unique number that has billions of permutations and is made up of a mixture of hexadecimal and numbers in groups. And it is generated based on the different factors, such as time, windows version, system resources such as hard disks, motherboards, devices and so on. A Guid is guaranteed to be unique. (Thanks ck!) I have not seen an instance where you do

Guid g = new Guid.NewGuid();
Guid g = Guid.NewGuid(); /* Thanks Dave! */

where g will have the same value in successive runs.

It is more commonly used for mutexes, an example would be to create a single instance of an application and by using a mutex with a guid guarantees the lifetime of the instance of the application.

Even, in some instances, it is used in the database but the method of using it is frowned upon.

Displeasure answered 11/12, 2009 at 14:7 Comment(2)
A GUID is NOT guaranteed to be unique, it is just very unlikely to generate two the same.Tusker
You don't need (indeed, can't use) the new keyword if using Guid.NewGuid()Cerelly

© 2022 - 2024 — McMap. All rights reserved.