[Mono-bugs] [Bug 75288][Maj] New - Mono.Data.SqliteClient does not marshal UTF-8 properly

bugzilla-daemon at bugzilla.ximian.com bugzilla-daemon at bugzilla.ximian.com
Thu Jun 16 19:43:54 EDT 2005


Please do not reply to this email- if you want to comment on the bug, go to the
URL shown below and enter your comments there.

Changed by edd at usefulinc.com.

http://bugzilla.ximian.com/show_bug.cgi?id=75288

--- shadow/75288	2005-06-16 19:43:54.000000000 -0400
+++ shadow/75288.tmp.4101	2005-06-16 19:43:54.000000000 -0400
@@ -0,0 +1,85 @@
+Bug#: 75288
+Product: Mono: Class Libraries
+Version: 1.1
+OS: 
+OS Details: Ubuntu Hoary, using tseng's packages
+Status: NEW   
+Resolution: 
+Severity: 
+Priority: Major
+Component: Sys.Data
+AssignedTo: mono-bugs at ximian.com                            
+ReportedBy: edd at usefulinc.com               
+QAContact: mono-bugs at ximian.com
+TargetMilestone: ---
+URL: 
+Cc: 
+Summary: Mono.Data.SqliteClient does not marshal UTF-8 properly
+
+I have a UTF-8 query that works fine from the sqlite command line tool, but
+not from when executed from a Mono program.
+
+Here's the query:
+
+INSERT INTO channel (url, title, description, imageurl, homepage,
+subscribed, category, fetched) VALUES
+('http://podcast.blogchina.com/podcast.xml', '博客中国-动听播客', '博客中国
+“动听播客”服务火热测试中', '', 'http://podcast.blogchina.com/', 0, '',
+632545581774313840);
+
+Here's the error from Mono:
+
+System.ApplicationException: Sqlite error near "00": syntax error
+in [0x0017d] (at
+/home/brandon/work/debian/mono-1.1.7/mcs/class/Mono.Data.SqliteClient/Mono.Data.SqliteClient/SqliteCommand.cs:256)
+Mono.Data.SqliteClient.SqliteCommand:ExecuteReader (CommandBehavior
+behavior, Boolean want_results, System.Int32 rows_affected)
+in [0x00005] (at
+/home/brandon/work/debian/mono-1.1.7/mcs/class/Mono.Data.SqliteClient/Mono.Data.SqliteClient/SqliteCommand.cs:178)
+
+
+The reason this happens is because the UTF-8 strings aren't being
+marshalled properly.  Mono's strings are UTF-16 inside.
+
+For Redland# we got around this by marshalling the UTF8 explicitly, I can
+provide pointers if required.
+
+I guess you need to detect whether the database is UTF8, UTF16 or what
+and do the Right Thing.
+
+Here are the two functions we made for Redland#.  We then didn't use
+'string', but IntPtr in our P/invoked declarations, and used these two
+functions to marshall data in and out.
+
+               public static IntPtr StringToHGlobalUTF8 (String s)
+               {
+                       if (s == null)
+                               return IntPtr.Zero;
+
+                       int len = System.Text.Encoding.UTF8.GetByteCount (s);
+                       byte [] bytes = new byte [len + 1];
+                       System.Text.Encoding.UTF8.GetBytes (s, 0, s.Length,
+bytes, 0);
+                       // set up 0 terminator
+                       bytes [len] = 0;
+                       
+                       IntPtr n = Marshal.AllocHGlobal (len + 1);
+                       Marshal.Copy (bytes, 0, n, len + 1);
+
+                       return n;
+               }
+
+               [DllImport ("libc", EntryPoint="strlen")]
+               static extern int strlen (IntPtr s);
+
+               public static String UTF8PtrToString (IntPtr p)
+               {
+                       if (p == IntPtr.Zero)
+                               return "";
+
+                       int len = strlen (p);
+                       byte [] bytes = new byte [len];
+                       Marshal.Copy (p, bytes, 0, len);
+                       return new String
+(System.Text.Encoding.UTF8.GetChars (bytes));
+               }


More information about the mono-bugs mailing list