mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-01-31 19:42:26 +00:00
DynamicSignal: Add Dispose to SignalInfo
SignalInfo implements IDisposable to free GCHandle. https://bugzilla.gnome.org/show_bug.cgi?id=793982
This commit is contained in:
parent
2d00f898fb
commit
b65093ab72
1 changed files with 15 additions and 4 deletions
|
@ -69,12 +69,13 @@ namespace Gst
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class SignalInfo
|
class SignalInfo : IDisposable
|
||||||
{
|
{
|
||||||
uint handlerId;
|
uint handlerId;
|
||||||
IntPtr closure;
|
IntPtr closure;
|
||||||
Delegate registeredHandler;
|
Delegate registeredHandler;
|
||||||
Type argsType;
|
Type argsType;
|
||||||
|
GCHandle gch;
|
||||||
|
|
||||||
public IntPtr Closure {
|
public IntPtr Closure {
|
||||||
get {
|
get {
|
||||||
|
@ -112,11 +113,12 @@ namespace Gst
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public SignalInfo (uint handlerId, IntPtr closure, Delegate registeredHandler)
|
public SignalInfo (uint handlerId, IntPtr closure, Delegate registeredHandler, GCHandle gch)
|
||||||
{
|
{
|
||||||
this.handlerId = handlerId;
|
this.handlerId = handlerId;
|
||||||
this.closure = closure;
|
this.closure = closure;
|
||||||
this.registeredHandler = registeredHandler;
|
this.registeredHandler = registeredHandler;
|
||||||
|
this.gch = gch;
|
||||||
|
|
||||||
if (!IsValidDelegate (registeredHandler))
|
if (!IsValidDelegate (registeredHandler))
|
||||||
throw new Exception ("Invalid delegate");
|
throw new Exception ("Invalid delegate");
|
||||||
|
@ -164,6 +166,13 @@ namespace Gst
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void Dispose ()
|
||||||
|
{
|
||||||
|
registeredHandler = null;
|
||||||
|
gch.Free ();
|
||||||
|
GC.SuppressFinalize (this);
|
||||||
|
}
|
||||||
|
|
||||||
public static bool IsValidDelegate (Delegate d)
|
public static bool IsValidDelegate (Delegate d)
|
||||||
{
|
{
|
||||||
MethodInfo mi = d.Method;
|
MethodInfo mi = d.Method;
|
||||||
|
@ -227,9 +236,10 @@ namespace Gst
|
||||||
|
|
||||||
// Let's allocate 64bytes for the GClosure, it should be more than necessary.
|
// Let's allocate 64bytes for the GClosure, it should be more than necessary.
|
||||||
IntPtr closure = g_closure_new_simple (64, IntPtr.Zero);
|
IntPtr closure = g_closure_new_simple (64, IntPtr.Zero);
|
||||||
g_closure_set_meta_marshal (closure, (IntPtr)GCHandle.Alloc (k), marshalHandler);
|
GCHandle gch = GCHandle.Alloc (k);
|
||||||
|
g_closure_set_meta_marshal (closure, (IntPtr)gch, marshalHandler);
|
||||||
uint signalId = g_signal_connect_closure (o.Handle, name, closure, after);
|
uint signalId = g_signal_connect_closure (o.Handle, name, closure, after);
|
||||||
SignalHandlers.Add (k, new SignalInfo (signalId, closure, handler));
|
SignalHandlers.Add (k, new SignalInfo (signalId, closure, handler, gch));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -242,6 +252,7 @@ namespace Gst
|
||||||
if (newHandler == null || handler == null) {
|
if (newHandler == null || handler == null) {
|
||||||
g_signal_handler_disconnect (o.Handle, si.HandlerId);
|
g_signal_handler_disconnect (o.Handle, si.HandlerId);
|
||||||
SignalHandlers.Remove (k);
|
SignalHandlers.Remove (k);
|
||||||
|
si.Dispose ();
|
||||||
} else {
|
} else {
|
||||||
si.RegisteredHandler = newHandler;
|
si.RegisteredHandler = newHandler;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue