The Labs \ Source Viewer \ SSCLI \ System \ Guid

  1. // ==++==
  2. //
  3. //
  4. // Copyright (c) 2006 Microsoft Corporation. All rights reserved.
  5. //
  6. // The use and distribution terms for this software are contained in the file
  7. // named license.txt, which can be found in the root of this distribution.
  8. // By using this software in any fashion, you are agreeing to be bound by the
  9. // terms of this license.
  10. //
  11. // You must not remove this notice, or any other, from this software.
  12. //
  13. //
  14. // ==--==
  15. namespace System
  16. {
  17.    
  18.     using System;
  19.     using System.Globalization;
  20.     using System.Text;
  21.     using System.Runtime.InteropServices;
  22.     using System.Runtime.CompilerServices;
  23.    
  24.     // Represents a Globally Unique Identifier.
  25.     [StructLayout(LayoutKind.Sequential)]
  26.     [Serializable()]
  27.     [System.Runtime.InteropServices.ComVisible(true)]
  28.     public struct Guid : IFormattable, IComparable, IComparable<Guid>, IEquatable<Guid>
  29.     {
  30.         public static readonly Guid Empty = new Guid();
  31.         ////////////////////////////////////////////////////////////////////////////////
  32.         // Member variables
  33.         ////////////////////////////////////////////////////////////////////////////////
  34.         private int _a;
  35.         private short _b;
  36.         private short _c;
  37.         private byte _d;
  38.         private byte _e;
  39.         private byte _f;
  40.         private byte _g;
  41.         private byte _h;
  42.         private byte _i;
  43.         private byte _j;
  44.         private byte _k;
  45.        
  46.        
  47.        
  48.         ////////////////////////////////////////////////////////////////////////////////
  49.         // Constructors
  50.         ////////////////////////////////////////////////////////////////////////////////
  51.        
  52.         // Creates a new guid from an array of bytes.
  53.         //
  54.         public Guid(byte[] b)
  55.         {
  56.             if (b == null)
  57.                 throw new ArgumentNullException("b");
  58.             if (b.Length != 16)
  59.                 throw new ArgumentException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Arg_GuidArrayCtor"), "16"));
  60.            
  61.             _a = ((int)b[3] << 24) | ((int)b[2] << 16) | ((int)b[1] << 8) | b[0];
  62.             _b = (short)(((int)b[5] << 8) | b[4]);
  63.             _c = (short)(((int)b[7] << 8) | b[6]);
  64.             _d = b[8];
  65.             _e = b[9];
  66.             _f = b[10];
  67.             _g = b[11];
  68.             _h = b[12];
  69.             _i = b[13];
  70.             _j = b[14];
  71.             _k = b[15];
  72.         }
  73.        
  74.         [CLSCompliant(false)]
  75.         public Guid(uint a, ushort b, ushort c, byte d, byte e, byte f, byte g, byte h, byte i, byte j,
  76.         byte k)
  77.         {
  78.             _a = (int)a;
  79.             _b = (short)b;
  80.             _c = (short)c;
  81.             _d = d;
  82.             _e = e;
  83.             _f = f;
  84.             _g = g;
  85.             _h = h;
  86.             _i = i;
  87.             _j = j;
  88.             _k = k;
  89.         }
  90.        
  91.         // Creates a new guid with all contents having value of 0
  92.         private Guid(bool blank)
  93.         {
  94.             // Must initialize value class members even if the native
  95.             // function reinitializes them. Compiler appeasement.
  96.             _a = 0;
  97.             _b = 0;
  98.             _c = 0;
  99.             _d = 0;
  100.             _e = 0;
  101.             _f = 0;
  102.             _g = 0;
  103.             _h = 0;
  104.             _i = 0;
  105.             _j = 0;
  106.             _k = 0;
  107.             if (!blank)
  108.                 CompleteGuid();
  109.         }
  110.        
  111.         // Creates a new guid based on the value in the string. The value is made up
  112.         // of hex digits speared by the dash ("-"). The string may begin and end with
  113.         // brackets ("{", "}").
  114.         //
  115.         // The string must be of the form dddddddd-dddd-dddd-dddd-dddddddddddd. where
  116.         // d is a hex digit. (That is 8 hex digits, followed by 4, then 4, then 4,
  117.         // then 12) such as: "CA761232-ED42-11CE-BACD-00AA0057B223"
  118.         //
  119.         public Guid(string g)
  120.         {
  121.             if (g == null) {
  122.                 throw new ArgumentNullException("g");
  123.             }
  124.            
  125.             int startPos = 0;
  126.             int temp;
  127.             long templ;
  128.             int currentPos = 0;
  129.            
  130.             try {
  131.                 // Check if it's of the form dddddddd-dddd-dddd-dddd-dddddddddddd
  132.                 if (g.IndexOf('-', 0) >= 0) {
  133.                    
  134.                     string guidString = g.Trim();
  135.                     //Remove Whitespace
  136.                     // check to see that it's the proper length
  137.                     if (guidString[0] == '{') {
  138.                         if (guidString.Length != 38 || guidString[37] != '}') {
  139.                             throw new FormatException(Environment.GetResourceString("Format_GuidInvLen"));
  140.                         }
  141.                         startPos = 1;
  142.                     }
  143.                     else if (guidString[0] == '(') {
  144.                         if (guidString.Length != 38 || guidString[37] != ')') {
  145.                             throw new FormatException(Environment.GetResourceString("Format_GuidInvLen"));
  146.                         }
  147.                         startPos = 1;
  148.                     }
  149.                     else if (guidString.Length != 36) {
  150.                         throw new FormatException(Environment.GetResourceString("Format_GuidInvLen"));
  151.                     }
  152.                     if (guidString[8 + startPos] != '-' || guidString[13 + startPos] != '-' || guidString[18 + startPos] != '-' || guidString[23 + startPos] != '-') {
  153.                         throw new FormatException(Environment.GetResourceString("Format_GuidDashes"));
  154.                     }
  155.                    
  156.                     currentPos = startPos;
  157.                     _a = TryParse(guidString, ref currentPos, 8);
  158.                     ++currentPos;
  159.                     //Increment past the '-';
  160.                     _b = (short)TryParse(guidString, ref currentPos, 4);
  161.                     ++currentPos;
  162.                     //Increment past the '-';
  163.                     _c = (short)TryParse(guidString, ref currentPos, 4);
  164.                     ++currentPos;
  165.                     //Increment past the '-';
  166.                     temp = TryParse(guidString, ref currentPos, 4);
  167.                     ++currentPos;
  168.                     //Increment past the '-';
  169.                     startPos = currentPos;
  170.                     templ = ParseNumbers.StringToLong(guidString, 16, ParseNumbers.NoSpace, ref currentPos);
  171.                     if (currentPos - startPos != 12) {
  172.                         throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidInvLen")));
  173.                     }
  174.                     _d = (byte)(temp >> 8);
  175.                     _e = (byte)(temp);
  176.                     temp = (int)(templ >> 32);
  177.                     _f = (byte)(temp >> 8);
  178.                     _g = (byte)(temp);
  179.                     temp = (int)(templ);
  180.                     _h = (byte)(temp >> 24);
  181.                     _i = (byte)(temp >> 16);
  182.                     _j = (byte)(temp >> 8);
  183.                     _k = (byte)(temp);
  184.                 }
  185.                 // Else check if it is of the form
  186.                 // {0xdddddddd,0xdddd,0xdddd,{0xdd,0xdd,0xdd,0xdd,0xdd,0xdd,0xdd,0xdd}}
  187.                 else if (g.IndexOf('{', 0) >= 0) {
  188.                     int numStart = 0;
  189.                     int numLen = 0;
  190.                    
  191.                     // Convert to lower case
  192.                     //g = g.ToLower();
  193.                    
  194.                     // Eat all of the whitespace
  195.                     g = EatAllWhitespace(g);
  196.                    
  197.                     // Check for leading '{'
  198.                     if (g[0] != '{')
  199.                         throw new FormatException(Environment.GetResourceString("Format_GuidBrace"));
  200.                    
  201.                     // Check for '0x'
  202.                     if (!IsHexPrefix(g, 1))
  203.                         throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidHexPrefix"), "{0xdddddddd, etc}"));
  204.                    
  205.                     // Find the end of this hex number (since it is not fixed length)
  206.                     numStart = 3;
  207.                     numLen = g.IndexOf(',', numStart) - numStart;
  208.                     if (numLen <= 0)
  209.                         throw new FormatException(Environment.GetResourceString("Format_GuidComma"));
  210.                    
  211.                     // Read in the number
  212.                         // first DWORD
  213.                         // hex
  214.                     _a = (int)ParseNumbers.StringToInt(g.Substring(numStart, numLen), 16, ParseNumbers.IsTight);
  215.                     // tight parsing
  216.                     // Check for '0x'
  217.                     if (!IsHexPrefix(g, numStart + numLen + 1))
  218.                         throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidHexPrefix"), "{0xdddddddd, 0xdddd, etc}"));
  219.                    
  220.                     // +3 to get by ',0x'
  221.                     numStart = numStart + numLen + 3;
  222.                     numLen = g.IndexOf(',', numStart) - numStart;
  223.                     if (numLen <= 0)
  224.                         throw new FormatException(Environment.GetResourceString("Format_GuidComma"));
  225.                    
  226.                     // Read in the number
  227.                         // first DWORD
  228.                         // hex
  229.                     _b = (short)ParseNumbers.StringToInt(g.Substring(numStart, numLen), 16, ParseNumbers.IsTight);
  230.                     // tight parsing
  231.                     // Check for '0x'
  232.                     if (!IsHexPrefix(g, numStart + numLen + 1))
  233.                         throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidHexPrefix"), "{0xdddddddd, 0xdddd, 0xdddd, etc}"));
  234.                    
  235.                     // +3 to get by ',0x'
  236.                     numStart = numStart + numLen + 3;
  237.                     numLen = g.IndexOf(',', numStart) - numStart;
  238.                     if (numLen <= 0)
  239.                         throw new FormatException(Environment.GetResourceString("Format_GuidComma"));
  240.                    
  241.                     // Read in the number
  242.                         // first DWORD
  243.                         // hex
  244.                     _c = (short)ParseNumbers.StringToInt(g.Substring(numStart, numLen), 16, ParseNumbers.IsTight);
  245.                     // tight parsing
  246.                     // Check for '{'
  247.                     if (g.Length <= numStart + numLen + 1 || g[numStart + numLen + 1] != '{')
  248.                         throw new FormatException(Environment.GetResourceString("Format_GuidBrace"));
  249.                    
  250.                     // Prepare for loop
  251.                     numLen++;
  252.                     byte[] bytes = new byte[8];
  253.                    
  254.                     for (int i = 0; i < 8; i++) {
  255.                         // Check for '0x'
  256.                         if (!IsHexPrefix(g, numStart + numLen + 1))
  257.                             throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidHexPrefix"), "{... { ... 0xdd, ...}}"));
  258.                        
  259.                         // +3 to get by ',0x' or '{0x' for first case
  260.                         numStart = numStart + numLen + 3;
  261.                        
  262.                         // Calculate number length
  263.                         // first 7 cases
  264.                         if (i < 7) {
  265.                             numLen = g.IndexOf(',', numStart) - numStart;
  266.                             if (numLen <= 0) {
  267.                                 throw new FormatException(Environment.GetResourceString("Format_GuidComma"));
  268.                             }
  269.                         }
  270.                         // last case ends with '}', not ','
  271.                         else {
  272.                             numLen = g.IndexOf('}', numStart) - numStart;
  273.                             if (numLen <= 0) {
  274.                                 throw new FormatException(Environment.GetResourceString("Format_GuidBraceAfterLastNumber"));
  275.                             }
  276.                         }
  277.                        
  278.                         // Read in the number
  279.                         uint number = (uint)Convert.ToInt32(g.Substring(numStart, numLen), 16);
  280.                         // check for overflow
  281.                         if (number > 255) {
  282.                             throw new FormatException(Environment.GetResourceString("Overflow_Byte"));
  283.                         }
  284.                         bytes[i] = (byte)number;
  285.                     }
  286.                    
  287.                     _d = bytes[0];
  288.                     _e = bytes[1];
  289.                     _f = bytes[2];
  290.                     _g = bytes[3];
  291.                     _h = bytes[4];
  292.                     _i = bytes[5];
  293.                     _j = bytes[6];
  294.                     _k = bytes[7];
  295.                    
  296.                     // Check for last '}'
  297.                     if (numStart + numLen + 1 >= g.Length || g[numStart + numLen + 1] != '}') {
  298.                         throw new FormatException(Environment.GetResourceString("Format_GuidEndBrace"));
  299.                     }
  300.                    
  301.                     // Check if we have extra characters at the end
  302.                     if (numStart + numLen + 1 != g.Length - 1) {
  303.                         throw new FormatException(Environment.GetResourceString("Format_ExtraJunkAtEnd"));
  304.                     }
  305.                    
  306.                     return;
  307.                 }
  308.                 // Check if it's of the form dddddddddddddddddddddddddddddddd
  309.                 else {
  310.                     string guidString = g.Trim();
  311.                     //Remove Whitespace
  312.                     if (guidString.Length != 32) {
  313.                         throw new FormatException(Environment.GetResourceString("Format_GuidInvLen"));
  314.                     }
  315.                    
  316.                     for (int i = 0; i < guidString.Length; i++) {
  317.                         char ch = guidString[i];
  318.                         if (ch >= '0' && ch <= '9') {
  319.                             continue;
  320.                         }
  321.                         else {
  322.                             char upperCaseCh = Char.ToUpper(ch, CultureInfo.InvariantCulture);
  323.                             if (upperCaseCh >= 'A' && upperCaseCh <= 'F') {
  324.                                 continue;
  325.                             }
  326.                         }
  327.                        
  328.                         throw new FormatException(Environment.GetResourceString("Format_GuidInvalidChar"));
  329.                     }
  330.                    
  331.                         // first DWORD
  332.                         // hex
  333.                     _a = (int)ParseNumbers.StringToInt(guidString.Substring(startPos, 8), 16, ParseNumbers.IsTight);
  334.                     // tight parsing
  335.                     startPos += 8;
  336.                     _b = (short)ParseNumbers.StringToInt(guidString.Substring(startPos, 4), 16, ParseNumbers.IsTight);
  337.                     startPos += 4;
  338.                     _c = (short)ParseNumbers.StringToInt(guidString.Substring(startPos, 4), 16, ParseNumbers.IsTight);
  339.                    
  340.                     startPos += 4;
  341.                     temp = (short)ParseNumbers.StringToInt(guidString.Substring(startPos, 4), 16, ParseNumbers.IsTight);
  342.                     startPos += 4;
  343.                     currentPos = startPos;
  344.                     templ = ParseNumbers.StringToLong(guidString, 16, startPos, ref currentPos);
  345.                     if (currentPos - startPos != 12) {
  346.                         throw new FormatException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Format_GuidInvLen")));
  347.                     }
  348.                     _d = (byte)(temp >> 8);
  349.                     _e = (byte)(temp);
  350.                     temp = (int)(templ >> 32);
  351.                     _f = (byte)(temp >> 8);
  352.                     _g = (byte)(temp);
  353.                     temp = (int)(templ);
  354.                     _h = (byte)(temp >> 24);
  355.                     _i = (byte)(temp >> 16);
  356.                     _j = (byte)(temp >> 8);
  357.                     _k = (byte)(temp);
  358.                 }
  359.             }
  360.             catch (IndexOutOfRangeException) {
  361.                 throw new FormatException(Environment.GetResourceString("Format_GuidUnrecognized"));
  362.             }
  363.         }
  364.        
  365.         // Creates a new GUID initialized to the value represented by the arguments.
  366.         //
  367.         public Guid(int a, short b, short c, byte[] d)
  368.         {
  369.             if (d == null)
  370.                 throw new ArgumentNullException("d");
  371.             // Check that array is not too big
  372.             if (d.Length != 8)
  373.                 throw new ArgumentException(String.Format(CultureInfo.CurrentCulture, Environment.GetResourceString("Arg_GuidArrayCtor"), "8"));
  374.            
  375.             _a = a;
  376.             _b = b;
  377.             _c = c;
  378.             _d = d[0];
  379.             _e = d[1];
  380.             _f = d[2];
  381.             _g = d[3];
  382.             _h = d[4];
  383.             _i = d[5];
  384.             _j = d[6];
  385.             _k = d[7];
  386.         }
  387.        
  388.         // Creates a new GUID initialized to the value represented by the
  389.         // arguments. The bytes are specified like this to avoid endianness issues.
  390.         //
  391.         public Guid(int a, short b, short c, byte d, byte e, byte f, byte g, byte h, byte i, byte j,
  392.         byte k)
  393.         {
  394.             _a = a;
  395.             _b = b;
  396.             _c = c;
  397.             _d = d;
  398.             _e = e;
  399.             _f = f;
  400.             _g = g;
  401.             _h = h;
  402.             _i = i;
  403.             _j = j;
  404.             _k = k;
  405.         }
  406.        
  407.        
  408.         private static int TryParse(string str, ref int parsePos, int requiredLength)
  409.         {
  410.             int currStart = parsePos;
  411.             // the exception message from ParseNumbers is better
  412.             int retVal = ParseNumbers.StringToInt(str, 16, ParseNumbers.NoSpace, ref parsePos);
  413.            
  414.             //If we didn't parse enough characters, there's clearly an error.
  415.             if (parsePos - currStart != requiredLength) {
  416.                 throw new FormatException(Environment.GetResourceString("Format_GuidInvalidChar"));
  417.             }
  418.             return retVal;
  419.         }
  420.        
  421.         private static string EatAllWhitespace(string str)
  422.         {
  423.             int newLength = 0;
  424.             char[] chArr = new char[str.Length];
  425.             char curChar;
  426.            
  427.             // Now get each char from str and if it is not whitespace add it to chArr
  428.             for (int i = 0; i < str.Length; i++) {
  429.                 curChar = str[i];
  430.                 if (!Char.IsWhiteSpace(curChar)) {
  431.                     chArr[newLength++] = curChar;
  432.                 }
  433.             }
  434.            
  435.             // Return a new string based on chArr
  436.             return new string(chArr, 0, newLength);
  437.         }
  438.        
  439.         private static bool IsHexPrefix(string str, int i)
  440.         {
  441.             if (str[i] == '0' && (Char.ToLower(str[i + 1], CultureInfo.InvariantCulture) == 'x'))
  442.                 return true;
  443.             else
  444.                 return false;
  445.         }
  446.        
  447.        
  448.         // Returns an unsigned byte array containing the GUID.
  449.         public byte[] ToByteArray()
  450.         {
  451.             byte[] g = new byte[16];
  452.            
  453.             g[0] = (byte)(_a);
  454.             g[1] = (byte)(_a >> 8);
  455.             g[2] = (byte)(_a >> 16);
  456.             g[3] = (byte)(_a >> 24);
  457.             g[4] = (byte)(_b);
  458.             g[5] = (byte)(_b >> 8);
  459.             g[6] = (byte)(_c);
  460.             g[7] = (byte)(_c >> 8);
  461.             g[8] = _d;
  462.             g[9] = _e;
  463.             g[10] = _f;
  464.             g[11] = _g;
  465.             g[12] = _h;
  466.             g[13] = _i;
  467.             g[14] = _j;
  468.             g[15] = _k;
  469.            
  470.             return g;
  471.         }
  472.        
  473.        
  474.         // Returns the guid in "registry" format.
  475.         public override string ToString()
  476.         {
  477.             return ToString("D", null);
  478.         }
  479.        
  480.         public override int GetHashCode()
  481.         {
  482.             return _a ^ (((int)_b << 16) | (int)(ushort)_c) ^ (((int)_f << 24) | _k);
  483.         }
  484.        
  485.         // Returns true if and only if the guid represented
  486.         // by o is the same as this instance.
  487.         public override bool Equals(object o)
  488.         {
  489.             Guid g;
  490.             // Check that o is a Guid first
  491.             if (o == null || !(o is Guid))
  492.                 return false;
  493.             else
  494.                 g = (Guid)o;
  495.            
  496.             // Now compare each of the elements
  497.             if (g._a != _a)
  498.                 return false;
  499.             if (g._b != _b)
  500.                 return false;
  501.             if (g._c != _c)
  502.                 return false;
  503.             if (g._d != _d)
  504.                 return false;
  505.             if (g._e != _e)
  506.                 return false;
  507.             if (g._f != _f)
  508.                 return false;
  509.             if (g._g != _g)
  510.                 return false;
  511.             if (g._h != _h)
  512.                 return false;
  513.             if (g._i != _i)
  514.                 return false;
  515.             if (g._j != _j)
  516.                 return false;
  517.             if (g._k != _k)
  518.                 return false;
  519.            
  520.             return true;
  521.         }
  522.        
  523.         public bool Equals(Guid g)
  524.         {
  525.             // Now compare each of the elements
  526.             if (g._a != _a)
  527.                 return false;
  528.             if (g._b != _b)
  529.                 return false;
  530.             if (g._c != _c)
  531.                 return false;
  532.             if (g._d != _d)
  533.                 return false;
  534.             if (g._e != _e)
  535.                 return false;
  536.             if (g._f != _f)
  537.                 return false;
  538.             if (g._g != _g)
  539.                 return false;
  540.             if (g._h != _h)
  541.                 return false;
  542.             if (g._i != _i)
  543.                 return false;
  544.             if (g._j != _j)
  545.                 return false;
  546.             if (g._k != _k)
  547.                 return false;
  548.            
  549.             return true;
  550.         }
  551.        
  552.         private int GetResult(uint me, uint them)
  553.         {
  554.             if (me < them) {
  555.                 return -1;
  556.             }
  557.             return 1;
  558.         }
  559.        
  560.         public int CompareTo(object value)
  561.         {
  562.             if (value == null) {
  563.                 return 1;
  564.             }
  565.             if (!(value is Guid)) {
  566.                 throw new ArgumentException(Environment.GetResourceString("Arg_MustBeGuid"));
  567.             }
  568.             Guid g = (Guid)value;
  569.            
  570.             if (g._a != this._a) {
  571.                 return GetResult((uint)this._a, (uint)g._a);
  572.             }
  573.            
  574.             if (g._b != this._b) {
  575.                 return GetResult((uint)this._b, (uint)g._b);
  576.             }
  577.            
  578.             if (g._c != this._c) {
  579.                 return GetResult((uint)this._c, (uint)g._c);
  580.             }
  581.            
  582.             if (g._d != this._d) {
  583.                 return GetResult((uint)this._d, (uint)g._d);
  584.             }
  585.            
  586.             if (g._e != this._e) {
  587.                 return GetResult((uint)this._e, (uint)g._e);
  588.             }
  589.            
  590.             if (g._f != this._f) {
  591.                 return GetResult((uint)this._f, (uint)g._f);
  592.             }
  593.            
  594.             if (g._g != this._g) {
  595.                 return GetResult((uint)this._g, (uint)g._g);
  596.             }
  597.            
  598.             if (g._h != this._h) {
  599.                 return GetResult((uint)this._h, (uint)g._h);
  600.             }
  601.            
  602.             if (g._i != this._i) {
  603.                 return GetResult((uint)this._i, (uint)g._i);
  604.             }
  605.            
  606.             if (g._j != this._j) {
  607.                 return GetResult((uint)this._j, (uint)g._j);
  608.             }
  609.            
  610.             if (g._k != this._k) {
  611.                 return GetResult((uint)this._k, (uint)g._k);
  612.             }
  613.            
  614.             return 0;
  615.         }
  616.        
  617.         public int CompareTo(Guid value)
  618.         {
  619.             if (value._a != this._a) {
  620.                 return GetResult((uint)this._a, (uint)value._a);
  621.             }
  622.            
  623.             if (value._b != this._b) {
  624.                 return GetResult((uint)this._b, (uint)value._b);
  625.             }
  626.            
  627.             if (value._c != this._c) {
  628.                 return GetResult((uint)this._c, (uint)value._c);
  629.             }
  630.            
  631.             if (value._d != this._d) {
  632.                 return GetResult((uint)this._d, (uint)value._d);
  633.             }
  634.            
  635.             if (value._e != this._e) {
  636.                 return GetResult((uint)this._e, (uint)value._e);
  637.             }
  638.            
  639.             if (value._f != this._f) {
  640.                 return GetResult((uint)this._f, (uint)value._f);
  641.             }
  642.            
  643.             if (value._g != this._g) {
  644.                 return GetResult((uint)this._g, (uint)value._g);
  645.             }
  646.            
  647.             if (value._h != this._h) {
  648.                 return GetResult((uint)this._h, (uint)value._h);
  649.             }
  650.            
  651.             if (value._i != this._i) {
  652.                 return GetResult((uint)this._i, (uint)value._i);
  653.             }
  654.            
  655.             if (value._j != this._j) {
  656.                 return GetResult((uint)this._j, (uint)value._j);
  657.             }
  658.            
  659.             if (value._k != this._k) {
  660.                 return GetResult((uint)this._k, (uint)value._k);
  661.             }
  662.            
  663.             return 0;
  664.         }
  665.        
  666.         public static bool operator ==(Guid a, Guid b)
  667.         {
  668.             // Now compare each of the elements
  669.             if (a._a != b._a)
  670.                 return false;
  671.             if (a._b != b._b)
  672.                 return false;
  673.             if (a._c != b._c)
  674.                 return false;
  675.             if (a._d != b._d)
  676.                 return false;
  677.             if (a._e != b._e)
  678.                 return false;
  679.             if (a._f != b._f)
  680.                 return false;
  681.             if (a._g != b._g)
  682.                 return false;
  683.             if (a._h != b._h)
  684.                 return false;
  685.             if (a._i != b._i)
  686.                 return false;
  687.             if (a._j != b._j)
  688.                 return false;
  689.             if (a._k != b._k)
  690.                 return false;
  691.            
  692.             return true;
  693.         }
  694.        
  695.         public static bool operator !=(Guid a, Guid b)
  696.         {
  697.             return !(a == b);
  698.         }
  699.        
  700.         // This will fill in the members of Guid using CoCreateGuid.
  701.         [MethodImplAttribute(MethodImplOptions.InternalCall)]
  702.         private extern void CompleteGuid();
  703.        
  704.         // This will create a new guid. Since we've now decided that constructors should 0-init,
  705.         // we need a method that allows users to create a guid.
  706.         public static Guid NewGuid()
  707.         {
  708.             return new Guid(false);
  709.         }
  710.        
  711.         public string ToString(string format)
  712.         {
  713.             return ToString(format, null);
  714.         }
  715.        
  716.         private static char HexToChar(int a)
  717.         {
  718.             a = a & 15;
  719.             return (char)((a > 9) ? a - 10 + 97 : a + 48);
  720.         }
  721.        
  722.         private static int HexsToChars(char[] guidChars, int offset, int a, int b)
  723.         {
  724.             guidChars[offset++] = HexToChar(a >> 4);
  725.             guidChars[offset++] = HexToChar(a);
  726.             guidChars[offset++] = HexToChar(b >> 4);
  727.             guidChars[offset++] = HexToChar(b);
  728.             return offset;
  729.         }
  730.        
  731.         // IFormattable interface
  732.         // We currently ignore provider
  733.         public string ToString(string format, IFormatProvider provider)
  734.         {
  735.             if (format == null || format.Length == 0)
  736.                 format = "D";
  737.            
  738.             char[] guidChars;
  739.             int offset = 0;
  740.             int strLength = 38;
  741.             bool dash = true;
  742.            
  743.             if (format.Length != 1) {
  744.                 // all acceptable format string are of length 1
  745.                 throw new FormatException(Environment.GetResourceString("Format_InvalidGuidFormatSpecification"));
  746.             }
  747.            
  748.             char formatCh = format[0];
  749.             if (formatCh == 'D' || formatCh == 'd') {
  750.                 guidChars = new char[36];
  751.                 strLength = 36;
  752.             }
  753.             else if (formatCh == 'N' || formatCh == 'n') {
  754.                 guidChars = new char[32];
  755.                 strLength = 32;
  756.                 dash = false;
  757.             }
  758.             else if (formatCh == 'B' || formatCh == 'b') {
  759.                 guidChars = new char[38];
  760.                 guidChars[offset++] = '{';
  761.                 guidChars[37] = '}';
  762.             }
  763.             else if (formatCh == 'P' || formatCh == 'p') {
  764.                 guidChars = new char[38];
  765.                 guidChars[offset++] = '(';
  766.                 guidChars[37] = ')';
  767.             }
  768.             else {
  769.                 throw new FormatException(Environment.GetResourceString("Format_InvalidGuidFormatSpecification"));
  770.             }
  771.            
  772.             offset = HexsToChars(guidChars, offset, _a >> 24, _a >> 16);
  773.             offset = HexsToChars(guidChars, offset, _a >> 8, _a);
  774.            
  775.             if (dash)
  776.                 guidChars[offset++] = '-';
  777.            
  778.             offset = HexsToChars(guidChars, offset, _b >> 8, _b);
  779.            
  780.             if (dash)
  781.                 guidChars[offset++] = '-';
  782.            
  783.             offset = HexsToChars(guidChars, offset, _c >> 8, _c);
  784.            
  785.             if (dash)
  786.                 guidChars[offset++] = '-';
  787.            
  788.             offset = HexsToChars(guidChars, offset, _d, _e);
  789.            
  790.             if (dash)
  791.                 guidChars[offset++] = '-';
  792.            
  793.             offset = HexsToChars(guidChars, offset, _f, _g);
  794.             offset = HexsToChars(guidChars, offset, _h, _i);
  795.             offset = HexsToChars(guidChars, offset, _j, _k);
  796.            
  797.             return new string(guidChars, 0, strLength);
  798.         }
  799.     }
  800. }

Developer Fusion