guid_unittest.cc 7.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231
  1. // Copyright (c) 2012 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "base/guid.h"
  5. #include <stdint.h>
  6. #include <limits>
  7. #include <set>
  8. #include <unordered_set>
  9. #include "base/strings/string_util.h"
  10. #include "build/build_config.h"
  11. #include "testing/gtest/include/gtest/gtest.h"
  12. namespace base {
  13. TEST(GUIDTest, GUIDGeneratesAllZeroes) {
  14. static constexpr uint64_t kBytes[] = {0, 0};
  15. const std::string clientid = RandomDataToGUIDString(kBytes);
  16. EXPECT_EQ("00000000-0000-0000-0000-000000000000", clientid);
  17. }
  18. TEST(GUIDTest, GUIDGeneratesCorrectly) {
  19. static constexpr uint64_t kBytes[] = {0x0123456789ABCDEFULL,
  20. 0xFEDCBA9876543210ULL};
  21. const std::string clientid = RandomDataToGUIDString(kBytes);
  22. EXPECT_EQ("01234567-89ab-cdef-fedc-ba9876543210", clientid);
  23. }
  24. TEST(GUIDTest, DeprecatedGUIDCorrectlyFormatted) {
  25. constexpr int kIterations = 10;
  26. for (int i = 0; i < kIterations; ++i) {
  27. const std::string guid = GenerateGUID();
  28. EXPECT_TRUE(IsValidGUID(guid));
  29. EXPECT_TRUE(IsValidGUIDOutputString(guid));
  30. EXPECT_TRUE(IsValidGUID(ToLowerASCII(guid)));
  31. EXPECT_TRUE(IsValidGUID(ToUpperASCII(guid)));
  32. }
  33. }
  34. TEST(GUIDTest, DeprecatedGUIDBasicUniqueness) {
  35. constexpr int kIterations = 10;
  36. for (int i = 0; i < kIterations; ++i) {
  37. const std::string guid_str1 = GenerateGUID();
  38. const std::string guid_str2 = GenerateGUID();
  39. EXPECT_EQ(36U, guid_str1.length());
  40. EXPECT_EQ(36U, guid_str2.length());
  41. EXPECT_NE(guid_str1, guid_str2);
  42. const GUID guid1 = GUID::ParseCaseInsensitive(guid_str1);
  43. EXPECT_TRUE(guid1.is_valid());
  44. const GUID guid2 = GUID::ParseCaseInsensitive(guid_str2);
  45. EXPECT_TRUE(guid2.is_valid());
  46. }
  47. }
  48. namespace {
  49. // The format of GUID version 4 must be xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx,
  50. // where y is one of [8, 9, a, b].
  51. bool IsValidV4(const GUID& guid) {
  52. const std::string& lowercase = guid.AsLowercaseString();
  53. return guid.is_valid() && lowercase[14] == '4' &&
  54. (lowercase[19] == '8' || lowercase[19] == '9' ||
  55. lowercase[19] == 'a' || lowercase[19] == 'b');
  56. }
  57. } // namespace
  58. TEST(GUIDTest, GUIDBasicUniqueness) {
  59. constexpr int kIterations = 10;
  60. for (int i = 0; i < kIterations; ++i) {
  61. const GUID guid1 = GUID::GenerateRandomV4();
  62. const GUID guid2 = GUID::GenerateRandomV4();
  63. EXPECT_NE(guid1, guid2);
  64. EXPECT_TRUE(guid1.is_valid());
  65. EXPECT_TRUE(IsValidV4(guid1));
  66. EXPECT_TRUE(guid2.is_valid());
  67. EXPECT_TRUE(IsValidV4(guid2));
  68. }
  69. }
  70. namespace {
  71. void TestGUIDValidity(StringPiece input, bool case_insensitive, bool strict) {
  72. SCOPED_TRACE(input);
  73. {
  74. const GUID guid = GUID::ParseCaseInsensitive(input);
  75. EXPECT_EQ(case_insensitive, guid.is_valid());
  76. }
  77. {
  78. const GUID guid = GUID::ParseLowercase(input);
  79. EXPECT_EQ(strict, guid.is_valid());
  80. }
  81. }
  82. } // namespace
  83. TEST(GUIDTest, Validity) {
  84. // Empty GUID is invalid.
  85. EXPECT_FALSE(GUID().is_valid());
  86. enum Parsability { kDoesntParse, kParsesCaseInsensitiveOnly, kAlwaysParses };
  87. static constexpr struct {
  88. StringPiece input;
  89. Parsability parsability;
  90. } kGUIDValidity[] = {
  91. {"invalid", kDoesntParse},
  92. {"0123456789ab-cdef-fedc-ba98-76543210", kDoesntParse},
  93. {"0123456789abcdeffedcba9876543210", kDoesntParse},
  94. {"01234567-89Zz-ZzZz-ZzZz-Zz9876543210", kDoesntParse},
  95. {"DEADBEEFDEADBEEFDEADBEEFDEADBEEF", kDoesntParse},
  96. {"deadbeefWdeadXbeefYdeadZbeefdeadbeef", kDoesntParse},
  97. {"XXXdeadbeefWdeadXbeefYdeadZbeefdeadbeefXXX", kDoesntParse},
  98. {"01234567-89aB-cDeF-fEdC-bA9876543210", kParsesCaseInsensitiveOnly},
  99. {"DEADBEEF-DEAD-BEEF-DEAD-BEEFDEADBEEF", kParsesCaseInsensitiveOnly},
  100. {"00000000-0000-0000-0000-000000000000", kAlwaysParses},
  101. {"deadbeef-dead-beef-dead-beefdeadbeef", kAlwaysParses},
  102. };
  103. for (const auto& validity : kGUIDValidity) {
  104. const bool case_insensitive = validity.parsability != kDoesntParse;
  105. const bool strict = validity.parsability == kAlwaysParses;
  106. TestGUIDValidity(validity.input, case_insensitive, strict);
  107. }
  108. }
  109. TEST(GUIDTest, Equality) {
  110. static constexpr uint64_t kBytes[] = {0xDEADBEEFDEADBEEFULL,
  111. 0xDEADBEEFDEADBEEFULL};
  112. const std::string clientid = RandomDataToGUIDString(kBytes);
  113. static constexpr char kExpectedCanonicalStr[] =
  114. "deadbeef-dead-beef-dead-beefdeadbeef";
  115. ASSERT_EQ(kExpectedCanonicalStr, clientid);
  116. const GUID from_lower = GUID::ParseCaseInsensitive(ToLowerASCII(clientid));
  117. EXPECT_EQ(kExpectedCanonicalStr, from_lower.AsLowercaseString());
  118. const GUID from_upper = GUID::ParseCaseInsensitive(ToUpperASCII(clientid));
  119. EXPECT_EQ(kExpectedCanonicalStr, from_upper.AsLowercaseString());
  120. EXPECT_EQ(from_lower, from_upper);
  121. // Invalid GUIDs are equal.
  122. EXPECT_EQ(GUID(), GUID());
  123. }
  124. TEST(GUIDTest, UnorderedSet) {
  125. std::unordered_set<GUID, GUIDHash> guid_set;
  126. static constexpr char kGUID1[] = "01234567-89ab-cdef-fedc-ba9876543210";
  127. guid_set.insert(GUID::ParseCaseInsensitive(ToLowerASCII(kGUID1)));
  128. EXPECT_EQ(1u, guid_set.size());
  129. guid_set.insert(GUID::ParseCaseInsensitive(ToUpperASCII(kGUID1)));
  130. EXPECT_EQ(1u, guid_set.size());
  131. static constexpr char kGUID2[] = "deadbeef-dead-beef-dead-beefdeadbeef";
  132. guid_set.insert(GUID::ParseCaseInsensitive(ToLowerASCII(kGUID2)));
  133. EXPECT_EQ(2u, guid_set.size());
  134. guid_set.insert(GUID::ParseCaseInsensitive(ToUpperASCII(kGUID2)));
  135. EXPECT_EQ(2u, guid_set.size());
  136. }
  137. TEST(GUIDTest, Set) {
  138. std::set<GUID> guid_set;
  139. static constexpr char kGUID1[] = "01234567-89ab-cdef-0123-456789abcdef";
  140. const GUID guid1 = GUID::ParseLowercase(kGUID1);
  141. ASSERT_TRUE(guid1.is_valid());
  142. guid_set.insert(guid1);
  143. static constexpr char kGUID2[] = "deadbeef-dead-beef-dead-beefdeadbeef";
  144. const GUID guid2 = GUID::ParseLowercase(kGUID2);
  145. ASSERT_TRUE(guid2.is_valid());
  146. guid_set.insert(guid2);
  147. // Test that the order of the GUIDs was preserved.
  148. auto it = guid_set.begin();
  149. EXPECT_EQ(guid1, *it);
  150. ++it;
  151. EXPECT_EQ(guid2, *it);
  152. ++it;
  153. EXPECT_EQ(guid_set.end(), it);
  154. }
  155. TEST(GUIDTest, Compare) {
  156. static constexpr char kGUID[] = "21abd97f-73e8-4b88-9389-a9fee6abda5e";
  157. static constexpr char kGUIDLess[] = "1e0dcaca-9e7c-4f4b-bcc6-e4c02b0c99df";
  158. static constexpr char kGUIDGreater[] = "6eeb1bc8-186b-433c-9d6a-a827bc96b2d4";
  159. const GUID guid = GUID::ParseLowercase(kGUID);
  160. const GUID guid_eq = GUID::ParseLowercase(kGUID);
  161. const GUID guid_lt = GUID::ParseLowercase(kGUIDLess);
  162. const GUID guid_gt = GUID::ParseLowercase(kGUIDGreater);
  163. const GUID guid_invalid = GUID();
  164. EXPECT_TRUE(guid_eq == guid);
  165. EXPECT_FALSE(guid_eq != guid);
  166. EXPECT_FALSE(guid_eq < guid);
  167. EXPECT_TRUE(guid_eq <= guid);
  168. EXPECT_FALSE(guid_eq > guid);
  169. EXPECT_TRUE(guid_eq >= guid);
  170. EXPECT_FALSE(guid_lt == guid);
  171. EXPECT_TRUE(guid_lt != guid);
  172. EXPECT_TRUE(guid_lt < guid);
  173. EXPECT_TRUE(guid_lt <= guid);
  174. EXPECT_FALSE(guid_lt > guid);
  175. EXPECT_FALSE(guid_lt >= guid);
  176. EXPECT_FALSE(guid_gt == guid);
  177. EXPECT_TRUE(guid_gt != guid);
  178. EXPECT_FALSE(guid_gt < guid);
  179. EXPECT_FALSE(guid_gt <= guid);
  180. EXPECT_TRUE(guid_gt > guid);
  181. EXPECT_TRUE(guid_gt >= guid);
  182. // Invalid GUIDs are the "least".
  183. EXPECT_FALSE(guid_invalid == guid);
  184. EXPECT_TRUE(guid_invalid != guid);
  185. EXPECT_TRUE(guid_invalid < guid);
  186. EXPECT_TRUE(guid_invalid <= guid);
  187. EXPECT_FALSE(guid_invalid > guid);
  188. EXPECT_FALSE(guid_invalid >= guid);
  189. }
  190. } // namespace base