From fe699e9fbb66c0135cdedf9613525c6fc2b89dc8 Mon Sep 17 00:00:00 2001 From: Rachel Hestilow Date: Tue, 10 Jun 2003 18:09:47 +0000 Subject: [PATCH] 2003-05-29 Rachel Hestilow * gconf/Value.cs: Update to use new string marshalling. * generator/StringGen.cs, ConstStringGen.cs: Added. * generator/IGeneratable.cs: Add new method ToNativeReturn. * generator/CallbackGen.cs: Implement ToNativeReturn. Call ToNativeReturn for the return statement. Fix a couple of places where s_ret was being used incorrectly for m_ret. * generator/ClassGen.cs, EnumGen.cs, ManualGen.cs, SimpleGen.cs, StructBase.cs: Implement ToNativeReturn. * generator/SignalHandler.cs: Call ToNativeReturn for the return statement, instead of CallByName. * generator/SymbolTable.cs: Use StringGen for gchar, char, and gunichar, and ConstStringGen for their const variants. Add a new method wrapper for ToNativeReturn. (Trim): Add a special-case for const strings so that the const is not stripped. Otherwise there is no way of resolving the const case. * glade/XML.custom: Update to use new string marshalling. * glib/Marshaller.cs: Added. * glib/GException.cs, Markup.cs, ObjectManager.cs, Value.cs: Update to use new string marshalling. * glib/Object.cs: Remove old g_type_name DllImport as it is no longer used. * glue/fileselection.c (gtksharp_file_selection_get_fileop_entry): Mark this as const return. * gtk/ColorSelection.custom, FileSelection.custom, SelectionData.custom: Update to use new string marshalling. svn path=/trunk/gtk-sharp/; revision=15286 --- ChangeLog | 34 ++++++++++++++++++++++++ gconf/GConf/Value.cs | 4 +-- generator/CallbackGen.cs | 9 +++++-- generator/ClassBase.cs | 5 ++++ generator/ConstStringGen.cs | 30 +++++++++++++++++++++ generator/EnumGen.cs | 5 ++++ generator/IGeneratable.cs | 2 ++ generator/ManualGen.cs | 5 ++++ generator/SignalHandler.cs | 2 +- generator/SimpleGen.cs | 5 ++++ generator/StringGen.cs | 28 ++++++++++++++++++++ generator/StructBase.cs | 6 +++++ generator/SymbolTable.cs | 24 +++++++++++++---- glade/XML.custom | 8 +++--- glib/GException.cs | 4 +-- glib/Markup.cs | 4 +-- glib/Marshaller.cs | 52 +++++++++++++++++++++++++++++++++++++ glib/Object.cs | 3 --- glib/ObjectManager.cs | 8 +++--- glib/Value.cs | 4 +-- glue/fileselection.c | 4 +-- gtk/ColorSelection.custom | 6 ++--- gtk/FileSelection.custom | 4 +-- gtk/SelectionData.custom | 4 +-- 24 files changed, 224 insertions(+), 36 deletions(-) create mode 100644 generator/ConstStringGen.cs create mode 100644 generator/StringGen.cs create mode 100644 glib/Marshaller.cs diff --git a/ChangeLog b/ChangeLog index 136c1627a..99cb429df 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,37 @@ +2003-05-29 Rachel Hestilow + + * gconf/Value.cs: Update to use new string marshalling. + + * generator/StringGen.cs, ConstStringGen.cs: Added. + * generator/IGeneratable.cs: Add new method ToNativeReturn. + * generator/CallbackGen.cs: Implement ToNativeReturn. Call + ToNativeReturn for the return statement. Fix a couple of + places where s_ret was being used incorrectly for m_ret. + * generator/ClassGen.cs, EnumGen.cs, ManualGen.cs, + SimpleGen.cs, StructBase.cs: Implement ToNativeReturn. + * generator/SignalHandler.cs: Call ToNativeReturn for the + return statement, instead of CallByName. + * generator/SymbolTable.cs: Use StringGen for gchar, char, + and gunichar, and ConstStringGen for their const variants. + Add a new method wrapper for ToNativeReturn. + (Trim): Add a special-case for const strings so that the + const is not stripped. Otherwise there is no way of + resolving the const case. + + * glade/XML.custom: Update to use new string marshalling. + + * glib/Marshaller.cs: Added. + * glib/GException.cs, Markup.cs, ObjectManager.cs, + Value.cs: Update to use new string marshalling. + * glib/Object.cs: Remove old g_type_name DllImport + as it is no longer used. + + * glue/fileselection.c (gtksharp_file_selection_get_fileop_entry): + Mark this as const return. + + * gtk/ColorSelection.custom, FileSelection.custom, + SelectionData.custom: Update to use new string marshalling. + 2003-06-07 Martin Willemoes Hansen * generator/SymbolTable.cs: Added ulong diff --git a/gconf/GConf/Value.cs b/gconf/GConf/Value.cs index ad471a753..9489bd184 100644 --- a/gconf/GConf/Value.cs +++ b/gconf/GConf/Value.cs @@ -88,7 +88,7 @@ namespace GConf } [DllImport("gconf-2")] - static extern string gconf_value_get_string (IntPtr value); + static extern IntPtr gconf_value_get_string (IntPtr value); [DllImport("gconf-2")] static extern int gconf_value_get_int (IntPtr value); @@ -104,7 +104,7 @@ namespace GConf switch (val_type) { case ValueType.String: - return gconf_value_get_string (Raw); + return Marshal.PtrToStringAnsi (gconf_value_get_string (Raw)); case ValueType.Int: return gconf_value_get_int (Raw); case ValueType.Float: diff --git a/generator/CallbackGen.cs b/generator/CallbackGen.cs index 90829a519..cc5693012 100644 --- a/generator/CallbackGen.cs +++ b/generator/CallbackGen.cs @@ -49,6 +49,11 @@ namespace GtkSharp.Generation { return FromNative (var); } + public virtual String ToNativeReturn(String var) + { + return CallByName (var); + } + public void GenWrapper (string ns) { char sep = Path.DirectorySeparatorChar; @@ -101,7 +106,7 @@ namespace GtkSharp.Generation { } else if (ret_wrapper != null && (ret_wrapper is ObjectGen || ret_wrapper is OpaqueGen)) { // Do nothing } else if (!table.IsStruct (rettype) && !table.IsBoxed (rettype)) { - sw.WriteLine ("\t\tstatic {0} _dummy;", s_ret); + sw.WriteLine ("\t\tstatic {0} _dummy;", m_ret); } } @@ -162,7 +167,7 @@ namespace GtkSharp.Generation { else if (table.IsEnum (rettype)) sw.WriteLine ("return (int) {0};", invoke); else - sw.WriteLine ("return ({0}) {1};", s_ret, invoke); + sw.WriteLine ("return ({0}) {1};", m_ret, table.ToNativeReturn (rettype, invoke)); } else sw.WriteLine (invoke + ";"); diff --git a/generator/ClassBase.cs b/generator/ClassBase.cs index a40993167..d4c829367 100644 --- a/generator/ClassBase.cs +++ b/generator/ClassBase.cs @@ -142,6 +142,11 @@ namespace GtkSharp.Generation { return FromNative (var); } + public virtual String ToNativeReturn(String var) + { + return CallByName (var); + } + protected void GenProperties (StreamWriter sw) { if (props == null) diff --git a/generator/ConstStringGen.cs b/generator/ConstStringGen.cs new file mode 100644 index 000000000..f1d0c6210 --- /dev/null +++ b/generator/ConstStringGen.cs @@ -0,0 +1,30 @@ +// GtkSharp.Generation.ConstStringGen.cs - The Const String type Generatable. +// +// Author: Rachel Hestilow +// +// (c) 2003 Rachel Hestilow + +namespace GtkSharp.Generation { + + using System; + + public class ConstStringGen : SimpleGen { + + public ConstStringGen (string ctype) : base (ctype, "string") + { + } + + public override String MarshalReturnType { + get + { + return "IntPtr"; + } + } + + public override String FromNativeReturn(String var) + { + return "Marshal.PtrToStringAnsi(" + var + ")"; + } + } +} + diff --git a/generator/EnumGen.cs b/generator/EnumGen.cs index 32ed0612e..26270fd24 100644 --- a/generator/EnumGen.cs +++ b/generator/EnumGen.cs @@ -42,6 +42,11 @@ namespace GtkSharp.Generation { return FromNative (var); } + public virtual String ToNativeReturn(String var) + { + return CallByName (var); + } + public void Generate () { if (!DoGenerate) diff --git a/generator/IGeneratable.cs b/generator/IGeneratable.cs index c412f1568..5e916ceda 100644 --- a/generator/IGeneratable.cs +++ b/generator/IGeneratable.cs @@ -26,6 +26,8 @@ namespace GtkSharp.Generation { String FromNativeReturn (String var); + String ToNativeReturn (String var); + bool DoGenerate {get;set;} void Generate (); diff --git a/generator/ManualGen.cs b/generator/ManualGen.cs index 2b1bd147e..436f08522 100644 --- a/generator/ManualGen.cs +++ b/generator/ManualGen.cs @@ -81,6 +81,11 @@ namespace GtkSharp.Generation { return FromNative (var); } + public virtual String ToNativeReturn(String var) + { + return CallByName (var); + } + public bool DoGenerate { get { return false; diff --git a/generator/SignalHandler.cs b/generator/SignalHandler.cs index 58fd6d7c9..e7169bd7f 100644 --- a/generator/SignalHandler.cs +++ b/generator/SignalHandler.cs @@ -162,7 +162,7 @@ namespace GtkSharp.Generation { else sw.WriteLine ("\t\t\t\tthrow new Exception(\"args.RetVal unset in callback\");"); - sw.WriteLine("\t\t\treturn (" + p_ret + ") " + table.CallByName (retval, "((" + s_ret + ")args.RetVal)") + ";"); + sw.WriteLine("\t\t\treturn (" + p_ret + ") " + table.ToNativeReturn (retval, "((" + s_ret + ")args.RetVal)") + ";"); } sw.WriteLine("\t\t}"); sw.WriteLine(); diff --git a/generator/SimpleGen.cs b/generator/SimpleGen.cs index 1a74fa720..5a0bbd078 100644 --- a/generator/SimpleGen.cs +++ b/generator/SimpleGen.cs @@ -68,6 +68,11 @@ namespace GtkSharp.Generation { return var; } + public String ToNativeReturn(String var) + { + return var; + } + public bool DoGenerate { get { return false; diff --git a/generator/StringGen.cs b/generator/StringGen.cs new file mode 100644 index 000000000..335be6b7a --- /dev/null +++ b/generator/StringGen.cs @@ -0,0 +1,28 @@ +// GtkSharp.Generation.StringGen.cs - The String type Generatable. +// +// Author: Rachel Hestilow +// +// (c) 2003 Rachel Hestilow + +namespace GtkSharp.Generation { + + using System; + + public class StringGen : ConstStringGen { + + public StringGen (string ctype) : base (ctype) + { + } + + public override String FromNativeReturn(String var) + { + return "GLibSharp.Marshaller.PtrToStringGFree(" + var + ")"; + } + + public override String ToNativeReturn(String var) + { + return "GLibSharp.Marshaller.StringToPtrGStrdup(" + var + ")"; + } + } +} + diff --git a/generator/StructBase.cs b/generator/StructBase.cs index 0466eafc4..67dd79462 100644 --- a/generator/StructBase.cs +++ b/generator/StructBase.cs @@ -81,6 +81,12 @@ namespace GtkSharp.Generation { return QualifiedName + ".New (" + var + ")"; } + public override String ToNativeReturn(String var) + { + // FIXME + return var; + } + bool IsBit (XmlElement field) { return (field.HasAttribute("bits") && (field.GetAttribute("bits") == "1")); diff --git a/generator/SymbolTable.cs b/generator/SymbolTable.cs index e8dd831c6..17a8ee961 100644 --- a/generator/SymbolTable.cs +++ b/generator/SymbolTable.cs @@ -39,9 +39,11 @@ namespace GtkSharp.Generation { AddType (new SimpleGen ("gushort", "ushort")); AddType (new SimpleGen ("guint32", "uint")); AddType (new SimpleGen ("guint64", "ulong")); - AddType (new SimpleGen ("const-gchar", "string")); - AddType (new SimpleGen ("const-char", "string")); - AddType (new SimpleGen ("gchar", "string")); + // Const returned strings must be generated + // differently from memory-managed strings + AddType (new ConstStringGen ("const-gchar")); + AddType (new ConstStringGen ("const-char")); + AddType (new StringGen ("gchar")); AddType (new SimpleGen ("gfloat", "float")); AddType (new SimpleGen ("gdouble", "double")); AddType (new SimpleGen ("gint8", "sbyte")); @@ -58,10 +60,10 @@ namespace GtkSharp.Generation { AddType (new SimpleGen ("gulong", "ulong")); AddType (new SimpleGen ("GQuark", "int")); AddType (new SimpleGen ("int", "int")); - AddType (new SimpleGen ("char", "string")); + AddType (new StringGen ("char")); AddType (new SimpleGen ("double", "double")); AddType (new SimpleGen ("float", "float")); - AddType (new SimpleGen ("gunichar", "string")); + AddType (new StringGen ("gunichar")); AddType (new SimpleGen ("uint1", "bool")); AddType (new SimpleGen ("GPtrArray", "IntPtr[]")); AddType (new SimpleGen ("GType", "uint")); @@ -128,6 +130,10 @@ namespace GtkSharp.Generation { if (type == "void*" || type == "const-void*") return "gpointer"; string trim_type = type.TrimEnd('*'); + + // HACK: Similar to above, but for const strings + if (trim_type == "const-gchar" || trim_type == "const-char") return trim_type; + if (trim_type.StartsWith("const-")) return trim_type.Substring(6); return trim_type; } @@ -148,6 +154,14 @@ namespace GtkSharp.Generation { return ""; return gen.FromNativeReturn (val); } + + public string ToNativeReturn(string c_type, string val) + { + IGeneratable gen = this[c_type]; + if (gen == null) + return ""; + return gen.ToNativeReturn (val); + } public string FromNative(string c_type, string val) { diff --git a/glade/XML.custom b/glade/XML.custom index ef8b1dd34..ab117967b 100644 --- a/glade/XML.custom +++ b/glade/XML.custom @@ -23,14 +23,14 @@ } [DllImport("gtksharpglue")] - static extern string gtksharp_glade_xml_get_filename (IntPtr raw); + static extern IntPtr gtksharp_glade_xml_get_filename (IntPtr raw); /// Filename Property /// Gets the filename used to create this GladeXML object /// public string Filename { get { - string ret = gtksharp_glade_xml_get_filename (Handle); + string ret = Marshal.PtrToStringAnsi (gtksharp_glade_xml_get_filename (Handle)); return ret; } } @@ -44,10 +44,10 @@ } [DllImport("libglade-2.0-0.dll")] - static extern string glade_get_widget_name (IntPtr widget); + static extern IntPtr glade_get_widget_name (IntPtr widget); static public string GetWidgetName (Gtk.Widget w) { - string ret = glade_get_widget_name (w.Handle); + string ret = Marshal.PtrToStringAnsi (glade_get_widget_name (w.Handle)); return ret; } diff --git a/glib/GException.cs b/glib/GException.cs index 9ce96468f..4379b7a85 100644 --- a/glib/GException.cs +++ b/glib/GException.cs @@ -19,10 +19,10 @@ namespace GLib { } [DllImport("gtksharpglue")] - static extern string gtksharp_error_get_message (IntPtr errptr); + static extern IntPtr gtksharp_error_get_message (IntPtr errptr); public override string Message { get { - return gtksharp_error_get_message (errptr); + return Marshal.PtrToStringAnsi (gtksharp_error_get_message (errptr)); } } diff --git a/glib/Markup.cs b/glib/Markup.cs index bf4225b20..5958e4a41 100644 --- a/glib/Markup.cs +++ b/glib/Markup.cs @@ -14,14 +14,14 @@ namespace GLib { public class Markup { [DllImport("libglib-2.0-0.dll")] - static extern string g_markup_escape_text (string text, int len); + static extern IntPtr g_markup_escape_text (string text, int len); static public string EscapeText (string s) { if (s == null) return ""; - return g_markup_escape_text (s, s.Length); + return GLibSharp.Marshaller.PtrToStringGFree (g_markup_escape_text (s, s.Length)); } } } diff --git a/glib/Marshaller.cs b/glib/Marshaller.cs new file mode 100644 index 000000000..a563602f2 --- /dev/null +++ b/glib/Marshaller.cs @@ -0,0 +1,52 @@ +// GLibSharp.Marshaller.cs : Marshalling utils +// +// Author: Rachel Hestilow +// +// (c) 2002, 2003 Rachel Hestilow + +namespace GLibSharp { + using System; + using System.Runtime.InteropServices; + + /// + /// Marshalling utilities + /// + /// + /// + /// Utility class for internal wrapper use + /// + + public class Marshaller { + + [DllImport("libglib-2.0-0.dll")] + static extern void g_free (IntPtr mem); + + public static string PtrToStringGFree (IntPtr ptr) { + string ret = Marshal.PtrToStringAnsi (ptr); + g_free (ptr); + return ret; + } + + [DllImport("libglib-2.0-0.dll")] + static extern void g_strfreev (IntPtr mem); + + public static string[] PtrToStringGFree (IntPtr[] ptrs) { + // The last pointer is a null terminator. + string[] ret = new string[ptrs.Length - 1]; + for (int i = 0; i < ret.Length; i++) { + ret[i] = Marshal.PtrToStringAnsi (ptrs[i]); + g_free (ptrs[i]); + } + return ret; + } + + [DllImport("libglib-2.0-0.dll")] + static extern IntPtr g_strdup (string str); + + public static IntPtr StringToPtrGStrdup (string str) { + return g_strdup (str); + } + + } +} + diff --git a/glib/Object.cs b/glib/Object.cs index fad5054d7..62716d614 100644 --- a/glib/Object.cs +++ b/glib/Object.cs @@ -236,9 +236,6 @@ namespace GLib { /// Handle property. /// - [DllImport("libgobject-2.0.so")] - private static extern string g_type_name (uint gtype); - protected virtual IntPtr Raw { get { return _obj; diff --git a/glib/ObjectManager.cs b/glib/ObjectManager.cs index 5d874e22c..f6b50b759 100644 --- a/glib/ObjectManager.cs +++ b/glib/ObjectManager.cs @@ -13,14 +13,14 @@ namespace GtkSharp { private static Hashtable types = new Hashtable (); [DllImport("gtksharpglue")] - static extern string gtksharp_get_type_name (IntPtr raw); + static extern IntPtr gtksharp_get_type_name (IntPtr raw); public static GLib.Object CreateObject (IntPtr raw) { if (raw == IntPtr.Zero) return null; - string typename = gtksharp_get_type_name (raw); + string typename = Marshal.PtrToStringAnsi (gtksharp_get_type_name (raw)); string mangled; if (types.ContainsKey(typename)) mangled = (string)types[typename]; @@ -88,7 +88,7 @@ namespace GtkSharp { static extern int gtksharp_get_parent_type (int typ); [DllImport("gtksharpglue")] - static extern string gtksharp_get_type_name_for_id (int typ); + static extern IntPtr gtksharp_get_type_name_for_id (int typ); static Type GetValidParentType (IntPtr raw) { @@ -99,7 +99,7 @@ namespace GtkSharp { // We will always end up at GObject and will break this loop while (true) { type_id = gtksharp_get_parent_type (type_id); - typename = gtksharp_get_type_name_for_id (type_id); + typename = Marshal.PtrToStringAnsi (gtksharp_get_type_name_for_id (type_id)); if (types.ContainsKey (typename)) mangled = (string)types[typename]; else diff --git a/glib/Value.cs b/glib/Value.cs index a9ebb4fd1..2f731ee21 100755 --- a/glib/Value.cs +++ b/glib/Value.cs @@ -517,7 +517,7 @@ namespace GLib { } [DllImport("libgobject-2.0-0.dll")] - static extern string g_value_get_string (IntPtr val); + static extern IntPtr g_value_get_string (IntPtr val); /// /// Value to String Conversion @@ -533,7 +533,7 @@ namespace GLib { { // FIXME: Insert an appropriate exception here if // _val.type indicates an error. - return g_value_get_string (val._val); + return Marshal.PtrToStringAnsi (g_value_get_string (val._val)); } [DllImport("libgobject-2.0-0.dll")] diff --git a/glue/fileselection.c b/glue/fileselection.c index 1ef0f8da7..b27000eb2 100644 --- a/glue/fileselection.c +++ b/glue/fileselection.c @@ -32,7 +32,7 @@ GtkWidget *gtksharp_file_selection_get_fileop_dialog (GtkFileSelection *file); GtkWidget *gtksharp_file_selection_get_fileop_entry (GtkFileSelection *file); -gchar *gtksharp_file_selection_get_fileop_file (GtkFileSelection *file); +const gchar *gtksharp_file_selection_get_fileop_file (GtkFileSelection *file); GtkWidget *gtksharp_file_selection_get_fileop_c_dir (GtkFileSelection *file); @@ -117,7 +117,7 @@ gtksharp_file_selection_get_fileop_entry (GtkFileSelection *file) return file->fileop_entry; } -gchar* +const gchar* gtksharp_file_selection_get_fileop_file (GtkFileSelection *file) { return file->fileop_file; diff --git a/gtk/ColorSelection.custom b/gtk/ColorSelection.custom index 2507cc3ae..3c64b00b3 100644 --- a/gtk/ColorSelection.custom +++ b/gtk/ColorSelection.custom @@ -3,13 +3,13 @@ // Author: Justin Malcolm [DllImport("libgtk-win32-2.0-0.dll")] - static extern string gtk_color_selection_palette_to_string(Gdk.Color[] colors, int n_colors); + static extern IntPtr gtk_color_selection_palette_to_string(Gdk.Color[] colors, int n_colors); /// PaletteToString Method public static string PaletteToString(Gdk.Color[] colors) { int n_colors = colors.Length; - string raw_ret = gtk_color_selection_palette_to_string(colors, n_colors); - string ret = raw_ret; + IntPtr raw_ret = gtk_color_selection_palette_to_string(colors, n_colors); + string ret = GLibSharp.Marshaller.PtrToStringGFree (raw_ret); return ret; } diff --git a/gtk/FileSelection.custom b/gtk/FileSelection.custom index 993d18c19..8d7044610 100644 --- a/gtk/FileSelection.custom +++ b/gtk/FileSelection.custom @@ -88,10 +88,10 @@ public Gtk.Entry FileopEntry { } [DllImport("gtksharpglue", CallingConvention=CallingConvention.Cdecl)] -static extern string gtksharp_file_selection_get_fileop_file (IntPtr i); +static extern IntPtr gtksharp_file_selection_get_fileop_file (IntPtr i); public string FileopFile { get { - return gtksharp_file_selection_get_fileop_file (this.Handle); + return Marshal.PtrToStringAnsi (gtksharp_file_selection_get_fileop_file (this.Handle)); } } diff --git a/gtk/SelectionData.custom b/gtk/SelectionData.custom index e5af01710..ad25ab27f 100644 --- a/gtk/SelectionData.custom +++ b/gtk/SelectionData.custom @@ -1,13 +1,13 @@ [DllImport("libgtk-win32-2.0-0.dll")] - private static extern string gtk_selection_data_get_text (ref Gtk.SelectionData selection_data); + private static extern IntPtr gtk_selection_data_get_text (ref Gtk.SelectionData selection_data); [DllImport("libgtk-win32-2.0-0.dll")] private static extern void gtk_selection_data_set_text (ref Gtk.SelectionData selection_data, string str, int len); public string Text { get { - return gtk_selection_data_get_text (ref this); + return GLibSharp.Marshaller.PtrToStringGFree (gtk_selection_data_get_text (ref this)); } set { gtk_selection_data_set_text (ref this, value, value.Length);