Unref mini objects immediately instead of 50ms later and fix mini object type registration

This commit is contained in:
Sebastian Dröge 2009-05-22 10:56:24 +02:00
parent 344a395f95
commit 61523d6d5a

View file

@ -69,8 +69,6 @@ namespace Gst {
IntPtr handle; IntPtr handle;
bool disposed = false; bool disposed = false;
static Hashtable Objects = new Hashtable(); static Hashtable Objects = new Hashtable();
static ArrayList PendingDestroys = new ArrayList ();
static bool idle_queued;
~MiniObject () { ~MiniObject () {
Dispose (); Dispose ();
@ -79,46 +77,21 @@ namespace Gst {
[DllImport ("gstreamer-0.10.dll") ] [DllImport ("gstreamer-0.10.dll") ]
static extern void gst_mini_object_unref (IntPtr raw); static extern void gst_mini_object_unref (IntPtr raw);
static bool PerformQueuedUnrefs () {
MiniObject [] objects;
lock (PendingDestroys) {
objects = new MiniObject [PendingDestroys.Count];
PendingDestroys.CopyTo (objects, 0);
PendingDestroys.Clear ();
}
lock (typeof (MiniObject))
idle_queued = false;
foreach (MiniObject o in objects) {
if (o.handle == IntPtr.Zero)
continue;
Objects.Remove (o.handle);
try {
gst_mini_object_unref (o.handle);
} catch (Exception e) {
Console.WriteLine ("Exception while disposing a " + o + " in Gtk#");
throw e;
}
o.handle = IntPtr.Zero;
}
return false;
}
public virtual void Dispose () { public virtual void Dispose () {
if (disposed) if (disposed)
return; return;
disposed = true; disposed = true;
lock (PendingDestroys) { lock (typeof (MiniObject)) {
PendingDestroys.Add (this); if (handle != IntPtr.Zero) {
lock (typeof (MiniObject)) { Objects.Remove (handle);
if (!idle_queued) { try {
Timeout.Add (50, new TimeoutHandler (PerformQueuedUnrefs)); gst_mini_object_unref (handle);
idle_queued = true; } catch (Exception e) {
Console.WriteLine ("Exception while disposing a " + this + " in Gtk#");
throw e;
} }
handle = IntPtr.Zero;
} }
} }
GC.SuppressFinalize (this); GC.SuppressFinalize (this);
@ -132,17 +105,17 @@ namespace Gst {
return null; return null;
MiniObject obj = null; MiniObject obj = null;
WeakReference weak_ref = Objects[o] as WeakReference; lock (typeof (MiniObject)) {
WeakReference weak_ref = Objects[o] as WeakReference;
if (weak_ref != null && weak_ref.IsAlive) if (weak_ref != null && weak_ref.IsAlive)
obj = weak_ref.Target as MiniObject; obj = weak_ref.Target as MiniObject;
if (obj == null) if (obj == null)
obj = Objects[o] as MiniObject; obj = Objects[o] as MiniObject;
}
if (obj != null && obj.handle == o) { if (obj != null && obj.handle == o) {
lock (PendingDestroys)
PendingDestroys.Remove (obj);
if (owned_ref) if (owned_ref)
gst_mini_object_unref (obj.handle); gst_mini_object_unref (obj.handle);
obj.disposed = false; obj.disposed = false;
@ -331,8 +304,6 @@ namespace Gst {
[DllImport ("glibsharpglue-2") ] [DllImport ("glibsharpglue-2") ]
static extern IntPtr gtksharp_register_type (IntPtr name, IntPtr parent_type); static extern IntPtr gtksharp_register_type (IntPtr name, IntPtr parent_type);
static Hashtable g_types = new Hashtable ();
protected GType LookupGType () { protected GType LookupGType () {
if (Handle != IntPtr.Zero) { if (Handle != IntPtr.Zero) {
GTypeInstance obj = (GTypeInstance) Marshal.PtrToStructure (Handle, typeof (GTypeInstance)); GTypeInstance obj = (GTypeInstance) Marshal.PtrToStructure (Handle, typeof (GTypeInstance));
@ -344,12 +315,9 @@ namespace Gst {
} }
protected internal static GType LookupGType (System.Type t) { protected internal static GType LookupGType (System.Type t) {
if (g_types.Contains (t)) GType gtype = (GType) t;
return (GType) g_types [t]; if (gtype.ToString () != "GtkSharpValue")
return gtype;
System.Reflection.PropertyInfo pi = t.GetProperty ("GType", BindingFlags.DeclaredOnly | BindingFlags.Static | BindingFlags.Public);
if (pi != null)
return (GType) pi.GetValue (null, null);
return RegisterGType (t); return RegisterGType (t);
} }