Author: atsushi
Date: 2006-01-16 04:41:40 -0500 (Mon, 16 Jan 2006)
New Revision: 55626

Modified:
   trunk/mcs/class/I18N/CJK/CP51932.cs
   trunk/mcs/class/I18N/CJK/ChangeLog
   trunk/mcs/class/I18N/CJK/Test/ChangeLog
   trunk/mcs/class/I18N/CJK/Test/I18N.CJK.Test.cs
Log:
2006-01-16  Atsushi Enomoto  <[EMAIL PROTECTED]>

        * CP51932.cs :
          In GetChars(), insufficient byte is not preserved.
          Under 1.x profile it is just discarded.
          Under 2.0 profile it is converted to \u30FB.
          Fixed GetCharCount() to match GetChars().

        * I18N.CJK.Test.cs : added test for bug #77223, #77224 and #77238.



Modified: trunk/mcs/class/I18N/CJK/CP51932.cs
===================================================================
--- trunk/mcs/class/I18N/CJK/CP51932.cs 2006-01-16 08:52:23 UTC (rev 55625)
+++ trunk/mcs/class/I18N/CJK/CP51932.cs 2006-01-16 09:41:40 UTC (rev 55626)
@@ -66,9 +66,6 @@
        // Internal state.
        private JISConvert convert;
 
-       // Conversion cache (note that encoding is not thread safe)
-       int lastByte;
-
        // Constructor.
        public CP51932 () : base (EUC_JP_CODE_PAGE)
        {
@@ -224,7 +221,6 @@
        }
 
        // Get the number of characters needed to decode a byte buffer.
-       // TODO: check
        public override int GetCharCount (byte [] bytes, int index, int count)
        {
                // Validate the parameters.
@@ -239,50 +235,96 @@
                        throw new ArgumentOutOfRangeException
                                ("count", Strings.GetString("ArgRange_Array"));
 
+
+
                // Determine the total length of the converted string.
+               int value = 0;
+               byte[] table0208 = convert.jisx0208ToUnicode;
+               byte[] table0212 = convert.jisx0212ToUnicode;
                int length = 0;
-               int byteval;
+               int byteval = 0;
                int last = 0;
 
                while (count > 0) {
                        byteval = bytes [index++];
                        --count;
-
                        if (last == 0) {
                                if (byteval == 0x8F) {
                                        if (byteval != 0) {
-                                               // Invalid second byte of a 
3-byte character
-                                               // FIXME: What should we do?
+                                               // Invalid second byte of a 
3-byte character.
                                                last = 0;
+                                               length++;
                                        }
                                        // First byte in a triple-byte sequence
                                        else
                                                last = byteval;
                                } else if (byteval <= 0x7F) {
                                        // Ordinary ASCII/Latin1/Control 
character.
-                                       ++length;
+                                       length++;
+                               } else if (byteval == 0x8E) {
+                                       // First byte of half-width Katakana
+                                       last = byteval;
                                } else if (byteval >= 0xA1 && byteval <= 0xFE) {
                                        // First byte in a double-byte sequence.
                                        last = byteval;
-                               } else if (byteval == 0x87) {
-                                       // First byte in half-width katakana
                                } else {
-                                       // Invalid first byte. Let '?'
-                                       ++length;
+                                       // Invalid first byte.
+                                       length++;
                                }
-                       } else if (last == 0x8F) {
+                       }
+                       else if (last == 0x8E) {
+                               if (byteval >= 0xA1 && byteval <= 0xDF) {
+                                       value = ((byteval - 0x40) |
+                                               (last + 0x71) << 8);
+                                       length++;
+                               } else {
+                                       // Invalid second byte.
+                                       length++;
+                               }
+                               last =0;
+                       }
+                       else if (last == 0x8F) {
                                // 3-byte character
                                // FIXME: currently not supported yet
-                               last = 0;
-                               ++length;
-                       } else {
+                               last = byteval;
+                       }
+                       else
+                       {
                                // Second byte in a double-byte sequence.
+                               value = (last - 0xA1) * 0x5E;
                                last = 0;
-                               ++length;
+                               if (byteval >= 0xA1 && byteval <= 0xFE)
+                               {
+                                       value += (byteval - 0xA1);
+                               }
+                               else
+                               {
+                                       // Invalid second byte.
+                                       last = 0;
+                                       length++;
+                                       continue;
+                               }
+
+                               value *= 2;
+                               value = ((int) (table0208 [value]))
+                                       | (((int) (table0208 [value + 1])) << 
8);
+                               if (value == 0)
+                                       value = ((int) (table0212 [value]))
+                                               | (((int) (table0212 [value + 
1])) << 8);
+                               if (value != 0)
+                                       length++;
+                               else
+                                       length++;
                        }
                }
+#if NET_2_0
+               // seems like .NET 2.0 adds \u30FB for insufficient
+               // byte seuqence (for Japanese \u30FB makes sense).
+               if (last != 0)
+                       length++;
+#endif
 
-               // Return the total length.
+               // Return the final length to the caller.
                return length;
        }
 
@@ -319,7 +361,7 @@
                int posn = charIndex;
                int charLength = chars.Length;
                int byteval, value;
-               int last = lastByte;
+               int last = 0;
                byte[] table0208 = convert.jisx0208ToUnicode;
                byte[] table0212 = convert.jisx0212ToUnicode;
 
@@ -327,22 +369,21 @@
                        byteval = bytes [byteIndex++];
                        --byteCount;
                        if (last == 0) {
-                               if (posn >= charLength)
-                                       throw new ArgumentException
-                                               (Strings.GetString
-                                                       
("Arg_InsufficientSpace"), "chars");
-
                                if (byteval == 0x8F) {
                                        if (byteval != 0) {
-                                               // Invalid second byte of a 
3-byte character
-                                               // FIXME: What should we do?
+                                               // Invalid second byte of a 
3-byte character.
                                                last = 0;
+                                               if (posn >= charLength)
+                                                       throw Insufficient ();
+                                               chars [posn++] = '?';
                                        }
                                        // First byte in a triple-byte sequence
                                        else
                                                last = byteval;
                                } else if (byteval <= 0x7F) {
                                        // Ordinary ASCII/Latin1/Control 
character.
+                                       if (posn >= charLength)
+                                               throw Insufficient ();
                                        chars [posn++] = (char) byteval;
                                } else if (byteval == 0x8E) {
                                        // First byte of half-width Katakana
@@ -352,6 +393,8 @@
                                        last = byteval;
                                } else {
                                        // Invalid first byte.
+                                       if (posn >= charLength)
+                                               throw Insufficient ();
                                        chars [posn++] = '?';
                                }
                        }
@@ -359,9 +402,13 @@
                                if (byteval >= 0xA1 && byteval <= 0xDF) {
                                        value = ((byteval - 0x40) |
                                                (last + 0x71) << 8);
+                                       if (posn >= charLength)
+                                               throw Insufficient ();
                                        chars [posn++] = (char) value;
                                } else {
                                        // Invalid second byte.
+                                       if (posn >= charLength)
+                                               throw Insufficient ();
                                        chars [posn++] = '?';
                                }
                                last =0;
@@ -383,7 +430,9 @@
                                else
                                {
                                        // Invalid second byte.
-                                       lastByte = 0;
+                                       last = 0;
+                                       if (posn >= charLength)
+                                               throw Insufficient ();
                                        chars [posn++] = '?';
                                        continue;
                                }
@@ -394,18 +443,35 @@
                                if (value == 0)
                                        value = ((int) (table0212 [value]))
                                                | (((int) (table0212 [value + 
1])) << 8);
+                               if (posn >= charLength)
+                                       throw Insufficient ();
                                if (value != 0)
                                        chars [posn++] = (char)value;
                                else
                                        chars [posn++] = '?';
                        }
                }
-               lastByte = last;
+#if NET_2_0
+               if (last != 0) {
+                       // seems like .NET 2.0 adds \u30FB for insufficient
+                       // byte seuqence (for Japanese \u30FB makes sense).
+                       if (posn >= charLength)
+                               throw Insufficient ();
+                       chars [posn++] = '\u30FB';
+               }
+#endif
 
                // Return the final length to the caller.
                return posn - charIndex;
        }
 
+       Exception Insufficient ()
+       {
+               throw new ArgumentException
+                       (Strings.GetString
+                               ("Arg_InsufficientSpace"), "chars");
+       }
+
        // Get the maximum number of bytes needed to encode a
        // specified number of characters.
        public override int GetMaxByteCount(int charCount)

Modified: trunk/mcs/class/I18N/CJK/ChangeLog
===================================================================
--- trunk/mcs/class/I18N/CJK/ChangeLog  2006-01-16 08:52:23 UTC (rev 55625)
+++ trunk/mcs/class/I18N/CJK/ChangeLog  2006-01-16 09:41:40 UTC (rev 55626)
@@ -1,3 +1,11 @@
+2006-01-16  Atsushi Enomoto  <[EMAIL PROTECTED]>
+
+       * CP51932.cs :
+         In GetChars(), insufficient byte is not preserved.
+         Under 1.x profile it is just discarded.
+         Under 2.0 profile it is converted to \u30FB.
+         Fixed GetCharCount() to match GetChars().
+
 2006-01-13  Atsushi Enomoto  <[EMAIL PROTECTED]>
 
        * CP932.cs : GetByteCount() returned insufficient count at PrivateUse

Modified: trunk/mcs/class/I18N/CJK/Test/ChangeLog
===================================================================
--- trunk/mcs/class/I18N/CJK/Test/ChangeLog     2006-01-16 08:52:23 UTC (rev 
55625)
+++ trunk/mcs/class/I18N/CJK/Test/ChangeLog     2006-01-16 09:41:40 UTC (rev 
55626)
@@ -1,3 +1,7 @@
+2006-01-16  Atsushi Enomoto  <[EMAIL PROTECTED]>
+
+       * I18N.CJK.Test.cs : added test for bug #77223, #77224 and #77238.
+
 2005-12-06  Atsushi Enomoto  <[EMAIL PROTECTED]>
 
        * I18N.CJK.Test.cs : w00t, Now all test are working, including

Modified: trunk/mcs/class/I18N/CJK/Test/I18N.CJK.Test.cs
===================================================================
--- trunk/mcs/class/I18N/CJK/Test/I18N.CJK.Test.cs      2006-01-16 08:52:23 UTC 
(rev 55625)
+++ trunk/mcs/class/I18N/CJK/Test/I18N.CJK.Test.cs      2006-01-16 09:41:40 UTC 
(rev 55626)
@@ -148,7 +148,7 @@
                        AssertDecode ("Test/texts/japanese-utf8.txt", 
"Test/texts/japanese-51932.txt", 51932);
                }
 
-               // ISI-2022-JP
+               // ISO-2022-JP
 
                [Test]
                public void CP50220_Encode ()
@@ -192,6 +192,36 @@
                        AssertDecode ("Test/texts/japanese-utf8.txt", 
"Test/texts/japanese-50222.txt", 50222);
                }
 
+               [Test]
+               public void Bug77723 ()
+               {
+                       Encoding e = Encoding.GetEncoding (51932);
+                       for (int i = 0; i < 0x10000; i++)
+                               e.GetBytes (new char [] { (char)i });
+               }
+
+               [Test]
+               public void Bug77224 ()
+               {
+                       Encoding e = Encoding.GetEncoding (932);
+                       for (int i = 0; i < 0x10000; i++)
+                               e.GetBytes (new char [] {(char) i});
+               }
+
+               [Test]
+               public void Bug77238 ()
+               {
+                       Encoding e = Encoding.GetEncoding (51932);
+                       byte [] bytes = new byte [2];
+                       for (int i0 = 0; i0 < 0x100; i0++) {
+                               bytes [0] = (byte) i0;
+                               for (int i1 = 0; i1 < 0x100; i1++) {
+                                       bytes [1] = (byte) i1;
+                                       e.GetChars (bytes);
+                               }
+                       }
+               }
+
                #endregion
 
                #region Korean

_______________________________________________
Mono-patches maillist  -  [email protected]
http://lists.ximian.com/mailman/listinfo/mono-patches

Reply via email to