/* GObject - GLib Type, Object, Parameter and Signal Library
 * Copyright (C) 2000-2001 Red Hat, Inc.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General
 * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
 *
 * this code is based on the original GtkSignal implementation
 * for the Gtk+ library by Peter Mattis <petm@xcf.berkeley.edu>
 */

/*
 * MT safe
 */

#include "config.h"

#include <string.h>
#include <signal.h>

#include "gsignal.h"
#include "gtype-private.h"
#include "gbsearcharray.h"
#include "gvaluecollector.h"
#include "gvaluetypes.h"
#include "gobject.h"
#include "genums.h"
#include "gobject_trace.h"


/**
 * SECTION:signals
 * @short_description: A means for customization of object behaviour
 *     and a general purpose notification mechanism
 * @title: Signals
 *
 * The basic concept of the signal system is that of the emission
 * of a signal. Signals are introduced per-type and are identified
 * through strings. Signals introduced for a parent type are available
 * in derived types as well, so basically they are a per-type facility
 * that is inherited.
 *
 * A signal emission mainly involves invocation of a certain set of
 * callbacks in precisely defined manner. There are two main categories
 * of such callbacks, per-object ones and user provided ones.
 * (Although signals can deal with any kind of instantiatable type, I'm
 * referring to those types as "object types" in the following, simply
 * because that is the context most users will encounter signals in.)
 * The per-object callbacks are most often referred to as "object method
 * handler" or "default (signal) handler", while user provided callbacks are
 * usually just called "signal handler".
 *
 * The object method handler is provided at signal creation time (this most
 * frequently happens at the end of an object class' creation), while user
 * provided handlers are frequently connected and disconnected to/from a
 * certain signal on certain object instances.
 *
 * A signal emission consists of five stages, unless prematurely stopped:
 *
 * 1. Invocation of the object method handler for %G_SIGNAL_RUN_FIRST signals
 *
 * 2. Invocation of normal user-provided signal handlers (where the @after
 *    flag is not set)
 *
 * 3. Invocation of the object method handler for %G_SIGNAL_RUN_LAST signals
 *
 * 4. Invocation of user provided signal handlers (where the @after flag is set)
 *
 * 5. Invocation of the object method handler for %G_SIGNAL_RUN_CLEANUP signals
 
 * The user-provided signal handlers are called in the order they were
 * connected in.
 *
 * All handlers may prematurely stop a signal emission, and any number of
 * handlers may be connected, disconnected, blocked or unblocked during
 * a signal emission.
 *
 * There are certain criteria for skipping user handlers in stages 2 and 4
 * of a signal emission.
 *
 * First, user handlers may be blocked. Blocked handlers are omitted during
 * callback invocation, to return from the blocked state, a handler has to
 * get unblocked exactly the same amount of times it has been blocked before.
 *
 * Second, upon emission of a %G_SIGNAL_DETAILED signal, an additional
 * @detail argument passed in to g_signal_emit() has to match the detail
 * argument of the signal handler currently subject to invocation.
 * Specification of no detail argument for signal handlers (omission of the
 * detail part of the signal specification upon connection) serves as a
 * wildcard and matches any detail argument passed in to emission.
 */


#define REPORT_BUG      "please report occurrence circumstances to gtk-devel-list@gnome.org"

/* --- typedefs --- */
typedef struct _SignalNode   SignalNode;
typedef struct _SignalKey    SignalKey;
typedef struct _Emission     Emission;
typedef struct _Handler      Handler;
typedef struct _HandlerList  HandlerList;
typedef struct _HandlerMatch HandlerMatch;
typedef enum
{
  EMISSION_STOP,
  EMISSION_RUN,
  EMISSION_HOOK,
  EMISSION_RESTART
} EmissionState;


/* --- prototypes --- */
static inline guint		signal_id_lookup	(GQuark		  quark,
							 GType		  itype);
static	      void		signal_destroy_R	(SignalNode	 *signal_node);
static inline HandlerList*	handler_list_ensure	(guint		  signal_id,
							 gpointer	  instance);
static inline HandlerList*	handler_list_lookup	(guint		  signal_id,
							 gpointer	  instance);
static inline Handler*		handler_new		(gboolean	  after);
static	      void		handler_insert		(guint		  signal_id,
							 gpointer	  instance,
							 Handler	 *handler);
static	      Handler*		handler_lookup		(gpointer	  instance,
							 gulong		  handler_id,
							 GClosure        *closure,
							 guint		 *signal_id_p);
static inline HandlerMatch*	handler_match_prepend	(HandlerMatch	 *list,
							 Handler	 *handler,
							 guint		  signal_id);
static inline HandlerMatch*	handler_match_free1_R	(HandlerMatch	 *node,
							 gpointer	  instance);
static	      HandlerMatch*	handlers_find		(gpointer	  instance,
							 GSignalMatchType mask,
							 guint		  signal_id,
							 GQuark		  detail,
							 GClosure	 *closure,
							 gpointer	  func,
							 gpointer	  data,
							 gboolean	  one_and_only);
static inline void		handler_ref		(Handler	 *handler);
static inline void		handler_unref_R		(guint		  signal_id,
							 gpointer	  instance,
							 Handler	 *handler);
static gint			handler_lists_cmp	(gconstpointer	  node1,
							 gconstpointer	  node2);
static inline void		emission_push		(Emission	**emission_list_p,
							 Emission	 *emission);
static inline void		emission_pop		(Emission	**emission_list_p,
							 Emission	 *emission);
static inline Emission*		emission_find		(Emission	 *emission_list,
							 guint		  signal_id,
							 GQuark		  detail,
							 gpointer	  instance);
static gint			class_closures_cmp	(gconstpointer	  node1,
							 gconstpointer	  node2);
static gint			signal_key_cmp		(gconstpointer	  node1,
							 gconstpointer	  node2);
static	      gboolean		signal_emit_unlocked_R	(SignalNode	 *node,
							 GQuark		  detail,
							 gpointer	  instance,
							 GValue		 *return_value,
							 const GValue	 *instance_and_params);
static       void               add_invalid_closure_notify    (Handler         *handler,
							       gpointer         instance);
static       void               remove_invalid_closure_notify (Handler         *handler,
							       gpointer         instance);
static       void               invalid_closure_notify  (gpointer         data,
							 GClosure        *closure);
static const gchar *            type_debug_name         (GType            type);
static void                     node_check_deprecated   (const SignalNode *node);
static void                     node_update_single_va_closure (SignalNode *node);


/* --- structures --- */
typedef struct
{
  GSignalAccumulator func;
  gpointer           data;
} SignalAccumulator;
typedef struct
{
  GHook hook;
  GQuark detail;
} SignalHook;
#define	SIGNAL_HOOK(hook)	((SignalHook*) (hook))

struct _SignalNode
{
  /* permanent portion */
  guint              signal_id;
  GType              itype;
  const gchar       *name;
  guint              destroyed : 1;
  
  /* reinitializable portion */
  guint              flags : 9;
  guint              n_params : 8;
  guint              single_va_closure_is_valid : 1;
  guint              single_va_closure_is_after : 1;
  GType		    *param_types; /* mangled with G_SIGNAL_TYPE_STATIC_SCOPE flag */
  GType		     return_type; /* mangled with G_SIGNAL_TYPE_STATIC_SCOPE flag */
  GBSearchArray     *class_closure_bsa;
  SignalAccumulator *accumulator;
  GSignalCMarshaller c_marshaller;
  GSignalCVaMarshaller va_marshaller;
  GHookList         *emission_hooks;

  GClosure *single_va_closure;
};

#define	SINGLE_VA_CLOSURE_EMPTY_MAGIC GINT_TO_POINTER(1)	/* indicates single_va_closure is valid but empty */

struct _SignalKey
{
  GType  itype;
  GQuark quark;
  guint  signal_id;
};

struct _Emission
{
  Emission             *next;
  gpointer              instance;
  GSignalInvocationHint ihint;
  EmissionState         state;
  GType			chain_type;
};

struct _HandlerList
{
  guint    signal_id;
  Handler *handlers;
  Handler *tail_before;  /* normal signal handlers are appended here  */
  Handler *tail_after;   /* CONNECT_AFTER handlers are appended here  */
};

struct _Handler
{
  gulong        sequential_number;
  Handler      *next;
  Handler      *prev;
  GQuark	detail;
  guint         ref_count;
  guint         block_count : 16;
#define HANDLER_MAX_BLOCK_COUNT (1 << 16)
  guint         after : 1;
  guint         has_invalid_closure_notify : 1;
  GClosure     *closure;
};
struct _HandlerMatch
{
  Handler      *handler;
  HandlerMatch *next;
  guint         signal_id;
};

typedef struct
{
  GType     instance_type; /* 0 for default closure */
  GClosure *closure;
} ClassClosure;


/* --- variables --- */
static GBSearchArray *g_signal_key_bsa = NULL;
static const GBSearchConfig g_signal_key_bconfig = {
  sizeof (SignalKey),
  signal_key_cmp,
  G_BSEARCH_ARRAY_ALIGN_POWER2,
};
static GBSearchConfig g_signal_hlbsa_bconfig = {
  sizeof (HandlerList),
  handler_lists_cmp,
  0,
};
static GBSearchConfig g_class_closure_bconfig = {
  sizeof (ClassClosure),
  class_closures_cmp,
  0,
};
static GHashTable    *g_handler_list_bsa_ht = NULL;
static Emission      *g_recursive_emissions = NULL;
static Emission      *g_restart_emissions = NULL;
static gulong         g_handler_sequential_number = 1;
G_LOCK_DEFINE_STATIC (g_signal_mutex);
#define	SIGNAL_LOCK()		G_LOCK (g_signal_mutex)
#define	SIGNAL_UNLOCK()		G_UNLOCK (g_signal_mutex)


/* --- signal nodes --- */
static guint          g_n_signal_nodes = 0;
static SignalNode   **g_signal_nodes = NULL;

static inline SignalNode*
LOOKUP_SIGNAL_NODE (guint signal_id)
{
  if (signal_id < g_n_signal_nodes)
    return g_signal_nodes[signal_id];
  else
    return NULL;
}


/* --- functions --- */
static inline guint
signal_id_lookup (GQuark quark,
		  GType  itype)
{
  GType *ifaces, type = itype;
  SignalKey key;
  guint n_ifaces;

  key.quark = quark;

  /* try looking up signals for this type and its ancestors */
  do
    {
      SignalKey *signal_key;
      
      key.itype = type;
      signal_key = g_bsearch_array_lookup (g_signal_key_bsa, &g_signal_key_bconfig, &key);
      
      if (signal_key)
	return signal_key->signal_id;
      
      type = g_type_parent (type);
    }
  while (type);

  /* no luck, try interfaces it exports */
  ifaces = g_type_interfaces (itype, &n_ifaces);
  while (n_ifaces--)
    {
      SignalKey *signal_key;

      key.itype = ifaces[n_ifaces];
      signal_key = g_bsearch_array_lookup (g_signal_key_bsa, &g_signal_key_bconfig, &key);

      if (signal_key)
	{
	  g_free (ifaces);
	  return signal_key->signal_id;
	}
    }
  g_free (ifaces);
  
  return 0;
}

static gint
class_closures_cmp (gconstpointer node1,
		    gconstpointer node2)
{
  const ClassClosure *c1 = node1, *c2 = node2;
  
  return G_BSEARCH_ARRAY_CMP (c1->instance_type, c2->instance_type);
}

static gint
handler_lists_cmp (gconstpointer node1,
                   gconstpointer node2)
{
  const HandlerList *hlist1 = node1, *hlist2 = node2;
  
  return G_BSEARCH_ARRAY_CMP (hlist1->signal_id, hlist2->signal_id);
}

static inline HandlerList*
handler_list_ensure (guint    signal_id,
		     gpointer instance)
{
  GBSearchArray *hlbsa = g_hash_table_lookup (g_handler_list_bsa_ht, instance);
  HandlerList key;
  
  key.signal_id = signal_id;
  key.handlers    = NULL;
  key.tail_before = NULL;
  key.tail_after  = NULL;
  if (!hlbsa)
    {
      hlbsa = g_bsearch_array_create (&g_signal_hlbsa_bconfig);
      hlbsa = g_bsearch_array_insert (hlbsa, &g_signal_hlbsa_bconfig, &key);
      g_hash_table_insert (g_handler_list_bsa_ht, instance, hlbsa);
    }
  else
    {
      GBSearchArray *o = hlbsa;

      hlbsa = g_bsearch_array_insert (o, &g_signal_hlbsa_bconfig, &key);
      if (hlbsa != o)
	g_hash_table_insert (g_handler_list_bsa_ht, instance, hlbsa);
    }
  return g_bsearch_array_lookup (hlbsa, &g_signal_hlbsa_bconfig, &key);
}

static inline HandlerList*
handler_list_lookup (guint    signal_id,
		     gpointer instance)
{
  GBSearchArray *hlbsa = g_hash_table_lookup (g_handler_list_bsa_ht, instance);
  HandlerList key;
  
  key.signal_id = signal_id;
  
  return hlbsa ? g_bsearch_array_lookup (hlbsa, &g_signal_hlbsa_bconfig, &key) : NULL;
}

static Handler*
handler_lookup (gpointer  instance,
		gulong    handler_id,
		GClosure *closure,
		guint    *signal_id_p)
{
  GBSearchArray *hlbsa = g_hash_table_lookup (g_handler_list_bsa_ht, instance);
  
  if (hlbsa)
    {
      guint i;
      
      for (i = 0; i < hlbsa->n_nodes; i++)
        {
          HandlerList *hlist = g_bsearch_array_get_nth (hlbsa, &g_signal_hlbsa_bconfig, i);
          Handler *handler;
          
          for (handler = hlist->handlers; handler; handler = handler->next)
            if (closure ? (handler->closure == closure) : (handler->sequential_number == handler_id))
              {
                if (signal_id_p)
                  *signal_id_p = hlist->signal_id;
		
                return handler;
              }
        }
    }
  
  return NULL;
}

static inline HandlerMatch*
handler_match_prepend (HandlerMatch *list,
		       Handler      *handler,
		       guint	     signal_id)
{
  HandlerMatch *node;
  
  node = g_slice_new (HandlerMatch);
  node->handler = handler;
  node->next = list;
  node->signal_id = signal_id;
  handler_ref (handler);
  
  return node;
}
static inline HandlerMatch*
handler_match_free1_R (HandlerMatch *node,
		       gpointer      instance)
{
  HandlerMatch *next = node->next;
  
  handler_unref_R (node->signal_id, instance, node->handler);
  g_slice_free (HandlerMatch, node);
  
  return next;
}

static HandlerMatch*
handlers_find (gpointer         instance,
	       GSignalMatchType mask,
	       guint            signal_id,
	       GQuark           detail,
	       GClosure        *closure,
	       gpointer         func,
	       gpointer         data,
	       gboolean         one_and_only)
{
  HandlerMatch *mlist = NULL;
  
  if (mask & G_SIGNAL_MATCH_ID)
    {
      HandlerList *hlist = handler_list_lookup (signal_id, instance);
      Handler *handler;
      SignalNode *node = NULL;
      
      if (mask & G_SIGNAL_MATCH_FUNC)
	{
	  node = LOOKUP_SIGNAL_NODE (signal_id);
	  if (!node || !node->c_marshaller)
	    return NULL;
	}
      
      mask = ~mask;
      for (handler = hlist ? hlist->handlers : NULL; handler; handler = handler->next)
        if (handler->sequential_number &&
	    ((mask & G_SIGNAL_MATCH_DETAIL) || handler->detail == detail) &&
	    ((mask & G_SIGNAL_MATCH_CLOSURE) || handler->closure == closure) &&
            ((mask & G_SIGNAL_MATCH_DATA) || handler->closure->data == data) &&
	    ((mask & G_SIGNAL_MATCH_UNBLOCKED) || handler->block_count == 0) &&
	    ((mask & G_SIGNAL_MATCH_FUNC) || (handler->closure->marshal == node->c_marshaller &&
					      G_REAL_CLOSURE (handler->closure)->meta_marshal == NULL &&
					      ((GCClosure*) handler->closure)->callback == func)))
	  {
	    mlist = handler_match_prepend (mlist, handler, signal_id);
	    if (one_and_only)
	      return mlist;
	  }
    }
  else
    {
      GBSearchArray *hlbsa = g_hash_table_lookup (g_handler_list_bsa_ht, instance);
      
      mask = ~mask;
      if (hlbsa)
        {
          guint i;
          
          for (i = 0; i < hlbsa->n_nodes; i++)
            {
              HandlerList *hlist = g_bsearch_array_get_nth (hlbsa, &g_signal_hlbsa_bconfig, i);
	      SignalNode *node = NULL;
              Handler *handler;
              
	      if (!(mask & G_SIGNAL_MATCH_FUNC))
		{
		  node = LOOKUP_SIGNAL_NODE (hlist->signal_id);
		  if (!node->c_marshaller)
		    continue;
		}
	      
              for (handler = hlist->handlers; handler; handler = handler->next)
		if (handler->sequential_number &&
		    ((mask & G_SIGNAL_MATCH_DETAIL) || handler->detail == detail) &&
                    ((mask & G_SIGNAL_MATCH_CLOSURE) || handler->closure == closure) &&
                    ((mask & G_SIGNAL_MATCH_DATA) || handler->closure->data == data) &&
		    ((mask & G_SIGNAL_MATCH_UNBLOCKED) || handler->block_count == 0) &&
		    ((mask & G_SIGNAL_MATCH_FUNC) || (handler->closure->marshal == node->c_marshaller &&
						      G_REAL_CLOSURE (handler->closure)->meta_marshal == NULL &&
						      ((GCClosure*) handler->closure)->callback == func)))
		  {
		    mlist = handler_match_prepend (mlist, handler, hlist->signal_id);
		    if (one_and_only)
		      return mlist;
		  }
            }
        }
    }
  
  return mlist;
}

static inline Handler*
handler_new (gboolean after)
{
  Handler *handler = g_slice_new (Handler);
#ifndef G_DISABLE_CHECKS
  if (g_handler_sequential_number < 1)
    g_error (G_STRLOC ": handler id overflow, %s", REPORT_BUG);
#endif
  
  handler->sequential_number = g_handler_sequential_number++;
  handler->prev = NULL;
  handler->next = NULL;
  handler->detail = 0;
  handler->ref_count = 1;
  handler->block_count = 0;
  handler->after = after != FALSE;
  handler->closure = NULL;
  handler->has_invalid_closure_notify = 0;
  
  return handler;
}

static inline void
handler_ref (Handler *handler)
{
  g_return_if_fail (handler->ref_count > 0);
  
  handler->ref_count++;
}

static inline void
handler_unref_R (guint    signal_id,
		 gpointer instance,
		 Handler *handler)
{
  g_return_if_fail (handler->ref_count > 0);

  handler->ref_count--;

  if (G_UNLIKELY (handler->ref_count == 0))
    {
      HandlerList *hlist = NULL;

      if (handler->next)
        handler->next->prev = handler->prev;
      if (handler->prev)    /* watch out for g_signal_handlers_destroy()! */
        handler->prev->next = handler->next;
      else
        {
          hlist = handler_list_lookup (signal_id, instance);
          hlist->handlers = handler->next;
        }

      if (instance)
        {
          /*  check if we are removing the handler pointed to by tail_before  */
          if (!handler->after && (!handler->next || handler->next->after))
            {
              if (!hlist)
                hlist = handler_list_lookup (signal_id, instance);
              if (hlist)
                {
                  g_assert (hlist->tail_before == handler); /* paranoid */
                  hlist->tail_before = handler->prev;
                }
            }

          /*  check if we are removing the handler pointed to by tail_after  */
          if (!handler->next)
            {
              if (!hlist)
                hlist = handler_list_lookup (signal_id, instance);
              if (hlist)
                {
                  g_assert (hlist->tail_after == handler); /* paranoid */
                  hlist->tail_after = handler->prev;
                }
            }
        }

      SIGNAL_UNLOCK ();
      g_closure_unref (handler->closure);
      SIGNAL_LOCK ();
      g_slice_free (Handler, handler);
    }
}

static void
handler_insert (guint    signal_id,
		gpointer instance,
		Handler  *handler)
{
  HandlerList *hlist;
  
  g_assert (handler->prev == NULL && handler->next == NULL); /* paranoid */
  
  hlist = handler_list_ensure (signal_id, instance);
  if (!hlist->handlers)
    {
      hlist->handlers = handler;
      if (!handler->after)
        hlist->tail_before = handler;
    }
  else if (handler->after)
    {
      handler->prev = hlist->tail_after;
      hlist->tail_after->next = handler;
    }
  else
    {
      if (hlist->tail_before)
        {
          handler->next = hlist->tail_before->next;
          if (handler->next)
            handler->next->prev = handler;
          handler->prev = hlist->tail_before;
          hlist->tail_before->next = handler;
        }
      else /* insert !after handler into a list of only after handlers */
        {
          handler->next = hlist->handlers;
          if (handler->next)
            handler->next->prev = handler;
          hlist->handlers = handler;
        }
      hlist->tail_before = handler;
    }

  if (!handler->next)
    hlist->tail_after = handler;
}

static void
node_update_single_va_closure (SignalNode *node)
{
  GClosure *closure = NULL;
  gboolean is_after = FALSE;

  /* Fast path single-handler without boxing the arguments in GValues */
  if (G_TYPE_IS_OBJECT (node->itype) &&
      (node->flags & (G_SIGNAL_MUST_COLLECT)) == 0 &&
      (node->emission_hooks == NULL || node->emission_hooks->hooks == NULL))
    {
      GSignalFlags run_type;
      ClassClosure * cc; 
      GBSearchArray *bsa = node->class_closure_bsa;

      if (bsa == NULL || bsa->n_nodes == 0)
	closure = SINGLE_VA_CLOSURE_EMPTY_MAGIC;
      else if (bsa->n_nodes == 1)
	{
	  /* Look for default class closure (can't support non-default as it
	     chains up using GValues */
	  cc = g_bsearch_array_get_nth (bsa, &g_class_closure_bconfig, 0);
	  if (cc->instance_type == 0)
	    {
	      run_type = node->flags & (G_SIGNAL_RUN_FIRST|G_SIGNAL_RUN_LAST|G_SIGNAL_RUN_CLEANUP);
	      /* Only support *one* of run-first or run-last, not multiple or cleanup */
	      if (run_type == G_SIGNAL_RUN_FIRST ||
		  run_type == G_SIGNAL_RUN_LAST)
		{
		  closure = cc->closure;
		  is_after = (run_type == G_SIGNAL_RUN_LAST);
		}
	    }
	}
    }

  node->single_va_closure_is_valid = TRUE;
  node->single_va_closure = closure;
  node->single_va_closure_is_after = is_after;
}

static inline void
emission_push (Emission **emission_list_p,
	       Emission  *emission)
{
  emission->next = *emission_list_p;
  *emission_list_p = emission;
}

static inline void
emission_pop (Emission **emission_list_p,
	      Emission  *emission)
{
  Emission *node, *last = NULL;

  for (node = *emission_list_p; node; last = node, node = last->next)
    if (node == emission)
      {
	if (last)
	  last->next = node->next;
	else
	  *emission_list_p = node->next;
	return;
      }
  g_assert_not_reached ();
}

static inline Emission*
emission_find (Emission *emission_list,
	       guint     signal_id,
	       GQuark    detail,
	       gpointer  instance)
{
  Emission *emission;
  
  for (emission = emission_list; emission; emission = emission->next)
    if (emission->instance == instance &&
	emission->ihint.signal_id == signal_id &&
	emission->ihint.detail == detail)
      return emission;
  return NULL;
}

static inline Emission*
emission_find_innermost (gpointer instance)
{
  Emission *emission, *s = NULL, *c = NULL;
  
  for (emission = g_restart_emissions; emission; emission = emission->next)
    if (emission->instance == instance)
      {
	s = emission;
	break;
      }
  for (emission = g_recursive_emissions; emission; emission = emission->next)
    if (emission->instance == instance)
      {
	c = emission;
	break;
      }
  if (!s)
    return c;
  else if (!c)
    return s;
  else
    return G_HAVE_GROWING_STACK ? MAX (c, s) : MIN (c, s);
}

static gint
signal_key_cmp (gconstpointer node1,
                gconstpointer node2)
{
  const SignalKey *key1 = node1, *key2 = node2;
  
  if (key1->itype == key2->itype)
    return G_BSEARCH_ARRAY_CMP (key1->quark, key2->quark);
  else
    return G_BSEARCH_ARRAY_CMP (key1->itype, key2->itype);
}

void
_g_signal_init (void)
{
  SIGNAL_LOCK ();
  if (!g_n_signal_nodes)
    {
      /* setup handler list binary searchable array hash table (in german, that'd be one word ;) */
      g_handler_list_bsa_ht = g_hash_table_new (g_direct_hash, NULL);
      g_signal_key_bsa = g_bsearch_array_create (&g_signal_key_bconfig);
      
      /* invalid (0) signal_id */
      g_n_signal_nodes = 1;
      g_signal_nodes = g_renew (SignalNode*, g_signal_nodes, g_n_signal_nodes);
      g_signal_nodes[0] = NULL;
    }
  SIGNAL_UNLOCK ();
}

void
_g_signals_destroy (GType itype)
{
  guint i;
  
  SIGNAL_LOCK ();
  for (i = 1; i < g_n_signal_nodes; i++)
    {
      SignalNode *node = g_signal_nodes[i];
      
      if (node->itype == itype)
        {
          if (node->destroyed)
            g_warning (G_STRLOC ": signal \"%s\" of type '%s' already destroyed",
                       node->name,
                       type_debug_name (node->itype));
          else
	    signal_destroy_R (node);
        }
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_stop_emission:
 * @instance: (type GObject.Object): the object whose signal handlers you wish to stop.
 * @signal_id: the signal identifier, as returned by g_signal_lookup().
 * @detail: the detail which the signal was emitted with.
 *
 * Stops a signal's current emission.
 *
 * This will prevent the default method from running, if the signal was
 * %G_SIGNAL_RUN_LAST and you connected normally (i.e. without the "after"
 * flag).
 *
 * Prints a warning if used on a signal which isn't being emitted.
 */
void
g_signal_stop_emission (gpointer instance,
                        guint    signal_id,
			GQuark   detail)
{
  SignalNode *node;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (signal_id > 0);
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (node && detail && !(node->flags & G_SIGNAL_DETAILED))
    {
      g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
      SIGNAL_UNLOCK ();
      return;
    }
  if (node && g_type_is_a (G_TYPE_FROM_INSTANCE (instance), node->itype))
    {
      Emission *emission_list = node->flags & G_SIGNAL_NO_RECURSE ? g_restart_emissions : g_recursive_emissions;
      Emission *emission = emission_find (emission_list, signal_id, detail, instance);
      
      if (emission)
        {
          if (emission->state == EMISSION_HOOK)
            g_warning (G_STRLOC ": emission of signal \"%s\" for instance '%p' cannot be stopped from emission hook",
                       node->name, instance);
          else if (emission->state == EMISSION_RUN)
            emission->state = EMISSION_STOP;
        }
      else
        g_warning (G_STRLOC ": no emission of signal \"%s\" to stop for instance '%p'",
                   node->name, instance);
    }
  else
    g_warning ("%s: signal id '%u' is invalid for instance '%p'", G_STRLOC, signal_id, instance);
  SIGNAL_UNLOCK ();
}

static void
signal_finalize_hook (GHookList *hook_list,
		      GHook     *hook)
{
  GDestroyNotify destroy = hook->destroy;

  if (destroy)
    {
      hook->destroy = NULL;
      SIGNAL_UNLOCK ();
      destroy (hook->data);
      SIGNAL_LOCK ();
    }
}

/**
 * g_signal_add_emission_hook:
 * @signal_id: the signal identifier, as returned by g_signal_lookup().
 * @detail: the detail on which to call the hook.
 * @hook_func: a #GSignalEmissionHook function.
 * @hook_data: user data for @hook_func.
 * @data_destroy: a #GDestroyNotify for @hook_data.
 *
 * Adds an emission hook for a signal, which will get called for any emission
 * of that signal, independent of the instance. This is possible only
 * for signals which don't have #G_SIGNAL_NO_HOOKS flag set.
 *
 * Returns: the hook id, for later use with g_signal_remove_emission_hook().
 */
gulong
g_signal_add_emission_hook (guint               signal_id,
			    GQuark              detail,
			    GSignalEmissionHook hook_func,
			    gpointer            hook_data,
			    GDestroyNotify      data_destroy)
{
  static gulong seq_hook_id = 1;
  SignalNode *node;
  GHook *hook;
  SignalHook *signal_hook;

  g_return_val_if_fail (signal_id > 0, 0);
  g_return_val_if_fail (hook_func != NULL, 0);

  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (!node || node->destroyed)
    {
      g_warning ("%s: invalid signal id '%u'", G_STRLOC, signal_id);
      SIGNAL_UNLOCK ();
      return 0;
    }
  if (node->flags & G_SIGNAL_NO_HOOKS) 
    {
      g_warning ("%s: signal id '%u' does not support emission hooks (G_SIGNAL_NO_HOOKS flag set)", G_STRLOC, signal_id);
      SIGNAL_UNLOCK ();
      return 0;
    }
  if (detail && !(node->flags & G_SIGNAL_DETAILED))
    {
      g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
      SIGNAL_UNLOCK ();
      return 0;
    }
    node->single_va_closure_is_valid = FALSE;
  if (!node->emission_hooks)
    {
      node->emission_hooks = g_new (GHookList, 1);
      g_hook_list_init (node->emission_hooks, sizeof (SignalHook));
      node->emission_hooks->finalize_hook = signal_finalize_hook;
    }

  node_check_deprecated (node);

  hook = g_hook_alloc (node->emission_hooks);
  hook->data = hook_data;
  hook->func = (gpointer) hook_func;
  hook->destroy = data_destroy;
  signal_hook = SIGNAL_HOOK (hook);
  signal_hook->detail = detail;
  node->emission_hooks->seq_id = seq_hook_id;
  g_hook_append (node->emission_hooks, hook);
  seq_hook_id = node->emission_hooks->seq_id;

  SIGNAL_UNLOCK ();

  return hook->hook_id;
}

/**
 * g_signal_remove_emission_hook:
 * @signal_id: the id of the signal
 * @hook_id: the id of the emission hook, as returned by
 *  g_signal_add_emission_hook()
 *
 * Deletes an emission hook.
 */
void
g_signal_remove_emission_hook (guint  signal_id,
			       gulong hook_id)
{
  SignalNode *node;

  g_return_if_fail (signal_id > 0);
  g_return_if_fail (hook_id > 0);

  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (!node || node->destroyed)
    {
      g_warning ("%s: invalid signal id '%u'", G_STRLOC, signal_id);
      goto out;
    }
  else if (!node->emission_hooks || !g_hook_destroy (node->emission_hooks, hook_id))
    g_warning ("%s: signal \"%s\" had no hook (%lu) to remove", G_STRLOC, node->name, hook_id);

  node->single_va_closure_is_valid = FALSE;

 out:
  SIGNAL_UNLOCK ();
}

static inline guint
signal_parse_name (const gchar *name,
		   GType        itype,
		   GQuark      *detail_p,
		   gboolean     force_quark)
{
  const gchar *colon = strchr (name, ':');
  guint signal_id;
  
  if (!colon)
    {
      signal_id = signal_id_lookup (g_quark_try_string (name), itype);
      if (signal_id && detail_p)
	*detail_p = 0;
    }
  else if (colon[1] == ':')
    {
      gchar buffer[32];
      guint l = colon - name;
      
      if (l < 32)
	{
	  memcpy (buffer, name, l);
	  buffer[l] = 0;
	  signal_id = signal_id_lookup (g_quark_try_string (buffer), itype);
	}
      else
	{
	  gchar *signal = g_new (gchar, l + 1);
	  
	  memcpy (signal, name, l);
	  signal[l] = 0;
	  signal_id = signal_id_lookup (g_quark_try_string (signal), itype);
	  g_free (signal);
	}
      
      if (signal_id && detail_p)
	*detail_p = colon[2] ? (force_quark ? g_quark_from_string : g_quark_try_string) (colon + 2) : 0;
    }
  else
    signal_id = 0;
  return signal_id;
}

/**
 * g_signal_parse_name:
 * @detailed_signal: a string of the form "signal-name::detail".
 * @itype: The interface/instance type that introduced "signal-name".
 * @signal_id_p: (out): Location to store the signal id.
 * @detail_p: (out): Location to store the detail quark.
 * @force_detail_quark: %TRUE forces creation of a #GQuark for the detail.
 *
 * Internal function to parse a signal name into its @signal_id
 * and @detail quark.
 *
 * Returns: Whether the signal name could successfully be parsed and @signal_id_p and @detail_p contain valid return values.
 */
gboolean
g_signal_parse_name (const gchar *detailed_signal,
		     GType        itype,
		     guint       *signal_id_p,
		     GQuark      *detail_p,
		     gboolean	  force_detail_quark)
{
  SignalNode *node;
  GQuark detail = 0;
  guint signal_id;
  
  g_return_val_if_fail (detailed_signal != NULL, FALSE);
  g_return_val_if_fail (G_TYPE_IS_INSTANTIATABLE (itype) || G_TYPE_IS_INTERFACE (itype), FALSE);
  
  SIGNAL_LOCK ();
  signal_id = signal_parse_name (detailed_signal, itype, &detail, force_detail_quark);
  SIGNAL_UNLOCK ();

  node = signal_id ? LOOKUP_SIGNAL_NODE (signal_id) : NULL;
  if (!node || node->destroyed ||
      (detail && !(node->flags & G_SIGNAL_DETAILED)))
    return FALSE;

  if (signal_id_p)
    *signal_id_p = signal_id;
  if (detail_p)
    *detail_p = detail;
  
  return TRUE;
}

/**
 * g_signal_stop_emission_by_name:
 * @instance: (type GObject.Object): the object whose signal handlers you wish to stop.
 * @detailed_signal: a string of the form "signal-name::detail".
 *
 * Stops a signal's current emission.
 *
 * This is just like g_signal_stop_emission() except it will look up the
 * signal id for you.
 */
void
g_signal_stop_emission_by_name (gpointer     instance,
				const gchar *detailed_signal)
{
  guint signal_id;
  GQuark detail = 0;
  GType itype;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (detailed_signal != NULL);
  
  SIGNAL_LOCK ();
  itype = G_TYPE_FROM_INSTANCE (instance);
  signal_id = signal_parse_name (detailed_signal, itype, &detail, TRUE);
  if (signal_id)
    {
      SignalNode *node = LOOKUP_SIGNAL_NODE (signal_id);
      
      if (detail && !(node->flags & G_SIGNAL_DETAILED))
	g_warning ("%s: signal '%s' does not support details", G_STRLOC, detailed_signal);
      else if (!g_type_is_a (itype, node->itype))
        g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
                   G_STRLOC, detailed_signal, instance, g_type_name (itype));
      else
	{
	  Emission *emission_list = node->flags & G_SIGNAL_NO_RECURSE ? g_restart_emissions : g_recursive_emissions;
	  Emission *emission = emission_find (emission_list, signal_id, detail, instance);
	  
	  if (emission)
	    {
	      if (emission->state == EMISSION_HOOK)
		g_warning (G_STRLOC ": emission of signal \"%s\" for instance '%p' cannot be stopped from emission hook",
			   node->name, instance);
	      else if (emission->state == EMISSION_RUN)
		emission->state = EMISSION_STOP;
	    }
	  else
	    g_warning (G_STRLOC ": no emission of signal \"%s\" to stop for instance '%p'",
		       node->name, instance);
	}
    }
  else
    g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
               G_STRLOC, detailed_signal, instance, g_type_name (itype));
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_lookup:
 * @name: the signal's name.
 * @itype: the type that the signal operates on.
 *
 * Given the name of the signal and the type of object it connects to, gets
 * the signal's identifying integer. Emitting the signal by number is
 * somewhat faster than using the name each time.
 *
 * Also tries the ancestors of the given type.
 *
 * See g_signal_new() for details on allowed signal names.
 *
 * Returns: the signal's identifying number, or 0 if no signal was found.
 */
guint
g_signal_lookup (const gchar *name,
                 GType        itype)
{
  guint signal_id;
  g_return_val_if_fail (name != NULL, 0);
  g_return_val_if_fail (G_TYPE_IS_INSTANTIATABLE (itype) || G_TYPE_IS_INTERFACE (itype), 0);
  
  SIGNAL_LOCK ();
  signal_id = signal_id_lookup (g_quark_try_string (name), itype);
  SIGNAL_UNLOCK ();
  if (!signal_id)
    {
      /* give elaborate warnings */
      if (!g_type_name (itype))
	g_warning (G_STRLOC ": unable to lookup signal \"%s\" for invalid type id '%"G_GSIZE_FORMAT"'",
		   name, itype);
      else if (!G_TYPE_IS_INSTANTIATABLE (itype))
	g_warning (G_STRLOC ": unable to lookup signal \"%s\" for non instantiatable type '%s'",
		   name, g_type_name (itype));
      else if (!g_type_class_peek (itype))
	g_warning (G_STRLOC ": unable to lookup signal \"%s\" of unloaded type '%s'",
		   name, g_type_name (itype));
    }
  
  return signal_id;
}

/**
 * g_signal_list_ids:
 * @itype: Instance or interface type.
 * @n_ids: Location to store the number of signal ids for @itype.
 *
 * Lists the signals by id that a certain instance or interface type
 * created. Further information about the signals can be acquired through
 * g_signal_query().
 *
 * Returns: (array length=n_ids): Newly allocated array of signal IDs.
 */
guint*
g_signal_list_ids (GType  itype,
		   guint *n_ids)
{
  SignalKey *keys;
  GArray *result;
  guint n_nodes;
  guint i;
  
  g_return_val_if_fail (G_TYPE_IS_INSTANTIATABLE (itype) || G_TYPE_IS_INTERFACE (itype), NULL);
  g_return_val_if_fail (n_ids != NULL, NULL);
  
  SIGNAL_LOCK ();
  keys = g_bsearch_array_get_nth (g_signal_key_bsa, &g_signal_key_bconfig, 0);
  n_nodes = g_bsearch_array_get_n_nodes (g_signal_key_bsa);
  result = g_array_new (FALSE, FALSE, sizeof (guint));
  
  for (i = 0; i < n_nodes; i++)
    if (keys[i].itype == itype)
      {
	const gchar *name = g_quark_to_string (keys[i].quark);
	
	/* Signal names with "_" in them are aliases to the same
	 * name with "-" instead of "_".
	 */
	if (!strchr (name, '_'))
	  g_array_append_val (result, keys[i].signal_id);
      }
  *n_ids = result->len;
  SIGNAL_UNLOCK ();
  if (!n_nodes)
    {
      /* give elaborate warnings */
      if (!g_type_name (itype))
	g_warning (G_STRLOC ": unable to list signals for invalid type id '%"G_GSIZE_FORMAT"'",
		   itype);
      else if (!G_TYPE_IS_INSTANTIATABLE (itype) && !G_TYPE_IS_INTERFACE (itype))
	g_warning (G_STRLOC ": unable to list signals of non instantiatable type '%s'",
		   g_type_name (itype));
      else if (!g_type_class_peek (itype) && !G_TYPE_IS_INTERFACE (itype))
	g_warning (G_STRLOC ": unable to list signals of unloaded type '%s'",
		   g_type_name (itype));
    }
  
  return (guint*) g_array_free (result, FALSE);
}

/**
 * g_signal_name:
 * @signal_id: the signal's identifying number.
 *
 * Given the signal's identifier, finds its name.
 *
 * Two different signals may have the same name, if they have differing types.
 *
 * Returns: the signal name, or %NULL if the signal number was invalid.
 */
const gchar *
g_signal_name (guint signal_id)
{
  SignalNode *node;
  const gchar *name;
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  name = node ? node->name : NULL;
  SIGNAL_UNLOCK ();
  
  return (char*) name;
}

/**
 * g_signal_query:
 * @signal_id: The signal id of the signal to query information for.
 * @query: (out caller-allocates): A user provided structure that is
 *  filled in with constant values upon success.
 *
 * Queries the signal system for in-depth information about a
 * specific signal. This function will fill in a user-provided
 * structure to hold signal-specific information. If an invalid
 * signal id is passed in, the @signal_id member of the #GSignalQuery
 * is 0. All members filled into the #GSignalQuery structure should
 * be considered constant and have to be left untouched.
 */
void
g_signal_query (guint         signal_id,
		GSignalQuery *query)
{
  SignalNode *node;
  
  g_return_if_fail (query != NULL);
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (!node || node->destroyed)
    query->signal_id = 0;
  else
    {
      query->signal_id = node->signal_id;
      query->signal_name = node->name;
      query->itype = node->itype;
      query->signal_flags = node->flags;
      query->return_type = node->return_type;
      query->n_params = node->n_params;
      query->param_types = node->param_types;
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_new:
 * @signal_name: the name for the signal
 * @itype: the type this signal pertains to. It will also pertain to
 *  types which are derived from this type.
 * @signal_flags: a combination of #GSignalFlags specifying detail of when
 *  the default handler is to be invoked. You should at least specify
 *  %G_SIGNAL_RUN_FIRST or %G_SIGNAL_RUN_LAST.
 * @class_offset: The offset of the function pointer in the class structure
 *  for this type. Used to invoke a class method generically. Pass 0 to
 *  not associate a class method slot with this signal.
 * @accumulator: the accumulator for this signal; may be %NULL.
 * @accu_data: user data for the @accumulator.
 * @c_marshaller: (allow-none): the function to translate arrays of parameter
 *  values to signal emissions into C language callback invocations or %NULL.
 * @return_type: the type of return value, or #G_TYPE_NONE for a signal
 *  without a return value.
 * @n_params: the number of parameter types to follow.
 * @...: a list of types, one for each parameter.
 *
 * Creates a new signal. (This is usually done in the class initializer.)
 *
 * A signal name consists of segments consisting of ASCII letters and
 * digits, separated by either the '-' or '_' character. The first
 * character of a signal name must be a letter. Names which violate these
 * rules lead to undefined behaviour of the GSignal system.
 *
 * When registering a signal and looking up a signal, either separator can
 * be used, but they cannot be mixed.
 *
 * If 0 is used for @class_offset subclasses cannot override the class handler
 * in their class_init method by doing super_class->signal_handler = my_signal_handler.
 * Instead they will have to use g_signal_override_class_handler().
 *
 * If c_marshaller is %NULL, g_cclosure_marshal_generic() will be used as
 * the marshaller for this signal.
 *
 * Returns: the signal id
 */
guint
g_signal_new (const gchar	 *signal_name,
	      GType		  itype,
	      GSignalFlags	  signal_flags,
	      guint               class_offset,
	      GSignalAccumulator  accumulator,
	      gpointer		  accu_data,
	      GSignalCMarshaller  c_marshaller,
	      GType		  return_type,
	      guint		  n_params,
	      ...)
{
  va_list args;
  guint signal_id;

  g_return_val_if_fail (signal_name != NULL, 0);
  
  va_start (args, n_params);

  signal_id = g_signal_new_valist (signal_name, itype, signal_flags,
                                   class_offset ? g_signal_type_cclosure_new (itype, class_offset) : NULL,
				   accumulator, accu_data, c_marshaller,
                                   return_type, n_params, args);

  va_end (args);

  return signal_id;
}

/**
 * g_signal_new_class_handler:
 * @signal_name: the name for the signal
 * @itype: the type this signal pertains to. It will also pertain to
 *  types which are derived from this type.
 * @signal_flags: a combination of #GSignalFlags specifying detail of when
 *  the default handler is to be invoked. You should at least specify
 *  %G_SIGNAL_RUN_FIRST or %G_SIGNAL_RUN_LAST.
 * @class_handler: a #GCallback which acts as class implementation of
 *  this signal. Used to invoke a class method generically. Pass %NULL to
 *  not associate a class method with this signal.
 * @accumulator: the accumulator for this signal; may be %NULL.
 * @accu_data: user data for the @accumulator.
 * @c_marshaller: (allow-none): the function to translate arrays of parameter
 *  values to signal emissions into C language callback invocations or %NULL.
 * @return_type: the type of return value, or #G_TYPE_NONE for a signal
 *  without a return value.
 * @n_params: the number of parameter types to follow.
 * @...: a list of types, one for each parameter.
 *
 * Creates a new signal. (This is usually done in the class initializer.)
 *
 * This is a variant of g_signal_new() that takes a C callback instead
 * off a class offset for the signal's class handler. This function
 * doesn't need a function pointer exposed in the class structure of
 * an object definition, instead the function pointer is passed
 * directly and can be overriden by derived classes with
 * g_signal_override_class_closure() or
 * g_signal_override_class_handler()and chained to with
 * g_signal_chain_from_overridden() or
 * g_signal_chain_from_overridden_handler().
 *
 * See g_signal_new() for information about signal names.
 *
 * If c_marshaller is %NULL, g_cclosure_marshal_generic() will be used as
 * the marshaller for this signal.
 *
 * Returns: the signal id
 *
 * Since: 2.18
 */
guint
g_signal_new_class_handler (const gchar        *signal_name,
                            GType               itype,
                            GSignalFlags        signal_flags,
                            GCallback           class_handler,
                            GSignalAccumulator  accumulator,
                            gpointer            accu_data,
                            GSignalCMarshaller  c_marshaller,
                            GType               return_type,
                            guint               n_params,
                            ...)
{
  va_list args;
  guint signal_id;

  g_return_val_if_fail (signal_name != NULL, 0);

  va_start (args, n_params);

  signal_id = g_signal_new_valist (signal_name, itype, signal_flags,
                                   class_handler ? g_cclosure_new (class_handler, NULL, NULL) : NULL,
                                   accumulator, accu_data, c_marshaller,
                                   return_type, n_params, args);

  va_end (args);

  return signal_id;
}

static inline ClassClosure*
signal_find_class_closure (SignalNode *node,
			   GType       itype)
{
  GBSearchArray *bsa = node->class_closure_bsa;
  ClassClosure *cc;

  if (bsa)
    {
      ClassClosure key;

      /* cc->instance_type is 0 for default closure */
      
      key.instance_type = itype;
      cc = g_bsearch_array_lookup (bsa, &g_class_closure_bconfig, &key);
      while (!cc && key.instance_type)
	{
	  key.instance_type = g_type_parent (key.instance_type);
	  cc = g_bsearch_array_lookup (bsa, &g_class_closure_bconfig, &key);
	}
    }
  else
    cc = NULL;
  return cc;
}

static inline GClosure*
signal_lookup_closure (SignalNode    *node,
		       GTypeInstance *instance)
{
  ClassClosure *cc;

  if (node->class_closure_bsa && g_bsearch_array_get_n_nodes (node->class_closure_bsa) == 1)
    {
      cc = g_bsearch_array_get_nth (node->class_closure_bsa, &g_class_closure_bconfig, 0);
      if (cc && cc->instance_type == 0) /* check for default closure */
        return cc->closure;
    }
  cc = signal_find_class_closure (node, G_TYPE_FROM_INSTANCE (instance));
  return cc ? cc->closure : NULL;
}

static void
signal_add_class_closure (SignalNode *node,
			  GType       itype,
			  GClosure   *closure)
{
  ClassClosure key;

  node->single_va_closure_is_valid = FALSE;

  if (!node->class_closure_bsa)
    node->class_closure_bsa = g_bsearch_array_create (&g_class_closure_bconfig);
  key.instance_type = itype;
  key.closure = g_closure_ref (closure);
  node->class_closure_bsa = g_bsearch_array_insert (node->class_closure_bsa,
						    &g_class_closure_bconfig,
						    &key);
  g_closure_sink (closure);
  if (node->c_marshaller && closure && G_CLOSURE_NEEDS_MARSHAL (closure))
    {
      g_closure_set_marshal (closure, node->c_marshaller);
      if (node->va_marshaller)
	_g_closure_set_va_marshal (closure, node->va_marshaller);
    }
}

/**
 * g_signal_newv:
 * @signal_name: the name for the signal
 * @itype: the type this signal pertains to. It will also pertain to
 *     types which are derived from this type
 * @signal_flags: a combination of #GSignalFlags specifying detail of when
 *     the default handler is to be invoked. You should at least specify
 *     %G_SIGNAL_RUN_FIRST or %G_SIGNAL_RUN_LAST
 * @class_closure: (allow-none): The closure to invoke on signal emission;
 *     may be %NULL
 * @accumulator: (allow-none): the accumulator for this signal; may be %NULL
 * @accu_data: user data for the @accumulator
 * @c_marshaller: (allow-none): the function to translate arrays of
 *     parameter values to signal emissions into C language callback
 *     invocations or %NULL
 * @return_type: the type of return value, or #G_TYPE_NONE for a signal
 *     without a return value
 * @n_params: the length of @param_types
 * @param_types: (array length=n_params): an array of types, one for
 *     each parameter
 *
 * Creates a new signal. (This is usually done in the class initializer.)
 *
 * See g_signal_new() for details on allowed signal names.
 *
 * If c_marshaller is %NULL, g_cclosure_marshal_generic() will be used as
 * the marshaller for this signal.
 *
 * Returns: the signal id
 */
guint
g_signal_newv (const gchar       *signal_name,
               GType              itype,
               GSignalFlags       signal_flags,
               GClosure          *class_closure,
               GSignalAccumulator accumulator,
	       gpointer		  accu_data,
               GSignalCMarshaller c_marshaller,
               GType		  return_type,
               guint              n_params,
               GType		 *param_types)
{
  gchar *name;
  guint signal_id, i;
  SignalNode *node;
  GSignalCMarshaller builtin_c_marshaller;
  GSignalCVaMarshaller va_marshaller;
  
  g_return_val_if_fail (signal_name != NULL, 0);
  g_return_val_if_fail (G_TYPE_IS_INSTANTIATABLE (itype) || G_TYPE_IS_INTERFACE (itype), 0);
  if (n_params)
    g_return_val_if_fail (param_types != NULL, 0);
  g_return_val_if_fail ((return_type & G_SIGNAL_TYPE_STATIC_SCOPE) == 0, 0);
  if (return_type == (G_TYPE_NONE & ~G_SIGNAL_TYPE_STATIC_SCOPE))
    g_return_val_if_fail (accumulator == NULL, 0);
  if (!accumulator)
    g_return_val_if_fail (accu_data == NULL, 0);

  name = g_strdup (signal_name);
  g_strdelimit (name, G_STR_DELIMITERS ":^", '_');  /* FIXME do character checks like for types */
  
  SIGNAL_LOCK ();
  
  signal_id = signal_id_lookup (g_quark_try_string (name), itype);
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (node && !node->destroyed)
    {
      g_warning (G_STRLOC ": signal \"%s\" already exists in the '%s' %s",
                 name,
                 type_debug_name (node->itype),
                 G_TYPE_IS_INTERFACE (node->itype) ? "interface" : "class ancestry");
      g_free (name);
      SIGNAL_UNLOCK ();
      return 0;
    }
  if (node && node->itype != itype)
    {
      g_warning (G_STRLOC ": signal \"%s\" for type '%s' was previously created for type '%s'",
                 name,
                 type_debug_name (itype),
                 type_debug_name (node->itype));
      g_free (name);
      SIGNAL_UNLOCK ();
      return 0;
    }
  for (i = 0; i < n_params; i++)
    if (!G_TYPE_IS_VALUE (param_types[i] & ~G_SIGNAL_TYPE_STATIC_SCOPE))
      {
	g_warning (G_STRLOC ": parameter %d of type '%s' for signal \"%s::%s\" is not a value type",
		   i + 1, type_debug_name (param_types[i]), type_debug_name (itype), name);
	g_free (name);
	SIGNAL_UNLOCK ();
	return 0;
      }
  if (return_type != G_TYPE_NONE && !G_TYPE_IS_VALUE (return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE))
    {
      g_warning (G_STRLOC ": return value of type '%s' for signal \"%s::%s\" is not a value type",
		 type_debug_name (return_type), type_debug_name (itype), name);
      g_free (name);
      SIGNAL_UNLOCK ();
      return 0;
    }
  if (return_type != G_TYPE_NONE &&
      (signal_flags & (G_SIGNAL_RUN_FIRST | G_SIGNAL_RUN_LAST | G_SIGNAL_RUN_CLEANUP)) == G_SIGNAL_RUN_FIRST)
    {
      g_warning (G_STRLOC ": signal \"%s::%s\" has return type '%s' and is only G_SIGNAL_RUN_FIRST",
		 type_debug_name (itype), name, type_debug_name (return_type));
      g_free (name);
      SIGNAL_UNLOCK ();
      return 0;
    }
  
  /* setup permanent portion of signal node */
  if (!node)
    {
      SignalKey key;
      
      signal_id = g_n_signal_nodes++;
      node = g_new (SignalNode, 1);
      node->signal_id = signal_id;
      g_signal_nodes = g_renew (SignalNode*, g_signal_nodes, g_n_signal_nodes);
      g_signal_nodes[signal_id] = node;
      node->itype = itype;
      node->name = name;
      key.itype = itype;
      key.quark = g_quark_from_string (node->name);
      key.signal_id = signal_id;
      g_signal_key_bsa = g_bsearch_array_insert (g_signal_key_bsa, &g_signal_key_bconfig, &key);
      g_strdelimit (name, "_", '-');
      node->name = g_intern_string (name);
      key.quark = g_quark_from_string (name);
      g_signal_key_bsa = g_bsearch_array_insert (g_signal_key_bsa, &g_signal_key_bconfig, &key);

      TRACE(GOBJECT_SIGNAL_NEW(signal_id, name, itype));
    }
  node->destroyed = FALSE;

  /* setup reinitializable portion */
  node->single_va_closure_is_valid = FALSE;
  node->flags = signal_flags & G_SIGNAL_FLAGS_MASK;
  node->n_params = n_params;
  node->param_types = g_memdup (param_types, sizeof (GType) * n_params);
  node->return_type = return_type;
  node->class_closure_bsa = NULL;
  if (accumulator)
    {
      node->accumulator = g_new (SignalAccumulator, 1);
      node->accumulator->func = accumulator;
      node->accumulator->data = accu_data;
    }
  else
    node->accumulator = NULL;

  builtin_c_marshaller = NULL;
  va_marshaller = NULL;

  /* Pick up built-in va marshallers for standard types, and
     instead of generic marshaller if no marshaller specified */
  if (n_params == 0 && return_type == G_TYPE_NONE)
    {
      builtin_c_marshaller = g_cclosure_marshal_VOID__VOID;
      va_marshaller = g_cclosure_marshal_VOID__VOIDv;
    }
  else if (n_params == 1 && return_type == G_TYPE_NONE)
    {
#define ADD_CHECK(__type__) \
      else if (g_type_is_a (param_types[0] & ~G_SIGNAL_TYPE_STATIC_SCOPE, G_TYPE_ ##__type__))         \
	{                                                                \
	  builtin_c_marshaller = g_cclosure_marshal_VOID__ ## __type__;  \
	  va_marshaller = g_cclosure_marshal_VOID__ ## __type__ ##v;     \
	}

      if (0) {}
      ADD_CHECK (BOOLEAN)
      ADD_CHECK (CHAR)
      ADD_CHECK (UCHAR)
      ADD_CHECK (INT)
      ADD_CHECK (UINT)
      ADD_CHECK (LONG)
      ADD_CHECK (ULONG)
      ADD_CHECK (ENUM)
      ADD_CHECK (FLAGS)
      ADD_CHECK (FLOAT)
      ADD_CHECK (DOUBLE)
      ADD_CHECK (STRING)
      ADD_CHECK (PARAM)
      ADD_CHECK (BOXED)
      ADD_CHECK (POINTER)
      ADD_CHECK (OBJECT)
      ADD_CHECK (VARIANT)
    }

  if (c_marshaller == NULL)
    {
      if (builtin_c_marshaller)
	c_marshaller = builtin_c_marshaller;
      else
	{
	  c_marshaller = g_cclosure_marshal_generic;
	  va_marshaller = g_cclosure_marshal_generic_va;
	}
    }

  node->c_marshaller = c_marshaller;
  node->va_marshaller = va_marshaller;
  node->emission_hooks = NULL;
  if (class_closure)
    signal_add_class_closure (node, 0, class_closure);

  SIGNAL_UNLOCK ();

  g_free (name);

  return signal_id;
}

void
g_signal_set_va_marshaller (guint              signal_id,
			    GType              instance_type,
			    GSignalCVaMarshaller va_marshaller)
{
  SignalNode *node;
  
  g_return_if_fail (signal_id > 0);
  g_return_if_fail (va_marshaller != NULL);
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (node)
    {
      node->va_marshaller = va_marshaller;
      if (node->class_closure_bsa)
	{
	  ClassClosure *cc = g_bsearch_array_get_nth (node->class_closure_bsa, &g_class_closure_bconfig, 0);
	  if (cc->closure->marshal == node->c_marshaller)
	    _g_closure_set_va_marshal (cc->closure, va_marshaller);
	}

      node->single_va_closure_is_valid = FALSE;
    }

  SIGNAL_UNLOCK ();
}


/**
 * g_signal_new_valist:
 * @signal_name: the name for the signal
 * @itype: the type this signal pertains to. It will also pertain to
 *  types which are derived from this type.
 * @signal_flags: a combination of #GSignalFlags specifying detail of when
 *  the default handler is to be invoked. You should at least specify
 *  %G_SIGNAL_RUN_FIRST or %G_SIGNAL_RUN_LAST.
 * @class_closure: The closure to invoke on signal emission; may be %NULL.
 * @accumulator: the accumulator for this signal; may be %NULL.
 * @accu_data: user data for the @accumulator.
 * @c_marshaller: (allow-none): the function to translate arrays of parameter
 *  values to signal emissions into C language callback invocations or %NULL.
 * @return_type: the type of return value, or #G_TYPE_NONE for a signal
 *  without a return value.
 * @n_params: the number of parameter types in @args.
 * @args: va_list of #GType, one for each parameter.
 *
 * Creates a new signal. (This is usually done in the class initializer.)
 *
 * See g_signal_new() for details on allowed signal names.
 *
 * If c_marshaller is %NULL, g_cclosure_marshal_generic() will be used as
 * the marshaller for this signal.
 *
 * Returns: the signal id
 */
guint
g_signal_new_valist (const gchar       *signal_name,
                     GType              itype,
                     GSignalFlags       signal_flags,
                     GClosure          *class_closure,
                     GSignalAccumulator accumulator,
		     gpointer		accu_data,
                     GSignalCMarshaller c_marshaller,
                     GType              return_type,
                     guint              n_params,
                     va_list            args)
{
  GType *param_types;
  guint i;
  guint signal_id;

  if (n_params > 0)
    {
      param_types = g_new (GType, n_params);

      for (i = 0; i < n_params; i++)
	param_types[i] = va_arg (args, GType);
    }
  else
    param_types = NULL;

  signal_id = g_signal_newv (signal_name, itype, signal_flags,
			     class_closure, accumulator, accu_data, c_marshaller,
			     return_type, n_params, param_types);
  g_free (param_types);

  return signal_id;
}

static void
signal_destroy_R (SignalNode *signal_node)
{
  SignalNode node = *signal_node;

  signal_node->destroyed = TRUE;
  
  /* reentrancy caution, zero out real contents first */
  signal_node->single_va_closure_is_valid = FALSE;
  signal_node->n_params = 0;
  signal_node->param_types = NULL;
  signal_node->return_type = 0;
  signal_node->class_closure_bsa = NULL;
  signal_node->accumulator = NULL;
  signal_node->c_marshaller = NULL;
  signal_node->va_marshaller = NULL;
  signal_node->emission_hooks = NULL;
  
#ifdef	G_ENABLE_DEBUG
  /* check current emissions */
  {
    Emission *emission;
    
    for (emission = (node.flags & G_SIGNAL_NO_RECURSE) ? g_restart_emissions : g_recursive_emissions;
         emission; emission = emission->next)
      if (emission->ihint.signal_id == node.signal_id)
        g_critical (G_STRLOC ": signal \"%s\" being destroyed is currently in emission (instance '%p')",
                    node.name, emission->instance);
  }
#endif
  
  /* free contents that need to
   */
  SIGNAL_UNLOCK ();
  g_free (node.param_types);
  if (node.class_closure_bsa)
    {
      guint i;

      for (i = 0; i < node.class_closure_bsa->n_nodes; i++)
	{
	  ClassClosure *cc = g_bsearch_array_get_nth (node.class_closure_bsa, &g_class_closure_bconfig, i);

	  g_closure_unref (cc->closure);
	}
      g_bsearch_array_free (node.class_closure_bsa, &g_class_closure_bconfig);
    }
  g_free (node.accumulator);
  if (node.emission_hooks)
    {
      g_hook_list_clear (node.emission_hooks);
      g_free (node.emission_hooks);
    }
  SIGNAL_LOCK ();
}

/**
 * g_signal_override_class_closure:
 * @signal_id: the signal id
 * @instance_type: the instance type on which to override the class closure
 *  for the signal.
 * @class_closure: the closure.
 *
 * Overrides the class closure (i.e. the default handler) for the given signal
 * for emissions on instances of @instance_type. @instance_type must be derived
 * from the type to which the signal belongs.
 *
 * See g_signal_chain_from_overridden() and
 * g_signal_chain_from_overridden_handler() for how to chain up to the
 * parent class closure from inside the overridden one.
 */
void
g_signal_override_class_closure (guint     signal_id,
				 GType     instance_type,
				 GClosure *class_closure)
{
  SignalNode *node;
  
  g_return_if_fail (signal_id > 0);
  g_return_if_fail (class_closure != NULL);
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  node_check_deprecated (node);
  if (!g_type_is_a (instance_type, node->itype))
    g_warning ("%s: type '%s' cannot be overridden for signal id '%u'", G_STRLOC, type_debug_name (instance_type), signal_id);
  else
    {
      ClassClosure *cc = signal_find_class_closure (node, instance_type);
      
      if (cc && cc->instance_type == instance_type)
	g_warning ("%s: type '%s' is already overridden for signal id '%u'", G_STRLOC, type_debug_name (instance_type), signal_id);
      else
	signal_add_class_closure (node, instance_type, class_closure);
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_override_class_handler:
 * @signal_name: the name for the signal
 * @instance_type: the instance type on which to override the class handler
 *  for the signal.
 * @class_handler: the handler.
 *
 * Overrides the class closure (i.e. the default handler) for the
 * given signal for emissions on instances of @instance_type with
 * callback @class_handler. @instance_type must be derived from the
 * type to which the signal belongs.
 *
 * See g_signal_chain_from_overridden() and
 * g_signal_chain_from_overridden_handler() for how to chain up to the
 * parent class closure from inside the overridden one.
 *
 * Since: 2.18
 */
void
g_signal_override_class_handler (const gchar *signal_name,
				 GType        instance_type,
				 GCallback    class_handler)
{
  guint signal_id;

  g_return_if_fail (signal_name != NULL);
  g_return_if_fail (instance_type != G_TYPE_NONE);
  g_return_if_fail (class_handler != NULL);

  signal_id = g_signal_lookup (signal_name, instance_type);

  if (signal_id)
    g_signal_override_class_closure (signal_id, instance_type,
                                     g_cclosure_new (class_handler, NULL, NULL));
  else
    g_warning ("%s: signal name '%s' is invalid for type id '%"G_GSIZE_FORMAT"'",
               G_STRLOC, signal_name, instance_type);

}

/**
 * g_signal_chain_from_overridden:
 * @instance_and_params: (array) the argument list of the signal emission.
 *  The first element in the array is a #GValue for the instance the signal
 *  is being emitted on. The rest are any arguments to be passed to the signal.
 * @return_value: Location for the return value.
 *
 * Calls the original class closure of a signal. This function should only
 * be called from an overridden class closure; see
 * g_signal_override_class_closure() and
 * g_signal_override_class_handler().
 */
void
g_signal_chain_from_overridden (const GValue *instance_and_params,
				GValue       *return_value)
{
  GType chain_type = 0, restore_type = 0;
  Emission *emission = NULL;
  GClosure *closure = NULL;
  guint n_params = 0;
  gpointer instance;
  
  g_return_if_fail (instance_and_params != NULL);
  instance = g_value_peek_pointer (instance_and_params);
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  
  SIGNAL_LOCK ();
  emission = emission_find_innermost (instance);
  if (emission)
    {
      SignalNode *node = LOOKUP_SIGNAL_NODE (emission->ihint.signal_id);
      
      g_assert (node != NULL);	/* paranoid */
      
      /* we should probably do the same parameter checks as g_signal_emit() here.
       */
      if (emission->chain_type != G_TYPE_NONE)
	{
	  ClassClosure *cc = signal_find_class_closure (node, emission->chain_type);
	  
	  g_assert (cc != NULL);	/* closure currently in call stack */

	  n_params = node->n_params;
	  restore_type = cc->instance_type;
	  cc = signal_find_class_closure (node, g_type_parent (cc->instance_type));
	  if (cc && cc->instance_type != restore_type)
	    {
	      closure = cc->closure;
	      chain_type = cc->instance_type;
	    }
	}
      else
	g_warning ("%s: signal id '%u' cannot be chained from current emission stage for instance '%p'", G_STRLOC, node->signal_id, instance);
    }
  else
    g_warning ("%s: no signal is currently being emitted for instance '%p'", G_STRLOC, instance);

  if (closure)
    {
      emission->chain_type = chain_type;
      SIGNAL_UNLOCK ();
      g_closure_invoke (closure,
			return_value,
			n_params + 1,
			instance_and_params,
			&emission->ihint);
      SIGNAL_LOCK ();
      emission->chain_type = restore_type;
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_chain_from_overridden_handler: (skip)
 * @instance: the instance the signal is being emitted on.
 * @...: parameters to be passed to the parent class closure, followed by a
 *  location for the return value. If the return type of the signal
 *  is #G_TYPE_NONE, the return value location can be omitted.
 *
 * Calls the original class closure of a signal. This function should
 * only be called from an overridden class closure; see
 * g_signal_override_class_closure() and
 * g_signal_override_class_handler().
 *
 * Since: 2.18
 */
void
g_signal_chain_from_overridden_handler (gpointer instance,
                                        ...)
{
  GType chain_type = 0, restore_type = 0;
  Emission *emission = NULL;
  GClosure *closure = NULL;
  SignalNode *node;
  guint n_params = 0;

  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));

  SIGNAL_LOCK ();
  emission = emission_find_innermost (instance);
  if (emission)
    {
      node = LOOKUP_SIGNAL_NODE (emission->ihint.signal_id);

      g_assert (node != NULL);	/* paranoid */

      /* we should probably do the same parameter checks as g_signal_emit() here.
       */
      if (emission->chain_type != G_TYPE_NONE)
	{
	  ClassClosure *cc = signal_find_class_closure (node, emission->chain_type);

	  g_assert (cc != NULL);	/* closure currently in call stack */

	  n_params = node->n_params;
	  restore_type = cc->instance_type;
	  cc = signal_find_class_closure (node, g_type_parent (cc->instance_type));
	  if (cc && cc->instance_type != restore_type)
	    {
	      closure = cc->closure;
	      chain_type = cc->instance_type;
	    }
	}
      else
	g_warning ("%s: signal id '%u' cannot be chained from current emission stage for instance '%p'", G_STRLOC, node->signal_id, instance);
    }
  else
    g_warning ("%s: no signal is currently being emitted for instance '%p'", G_STRLOC, instance);

  if (closure)
    {
      GValue *instance_and_params;
      GType signal_return_type;
      GValue *param_values;
      va_list var_args;
      guint i;

      va_start (var_args, instance);

      signal_return_type = node->return_type;
      instance_and_params = g_alloca (sizeof (GValue) * (n_params + 1));
      memset (instance_and_params, 0, sizeof (GValue) * (n_params + 1));
      param_values = instance_and_params + 1;

      for (i = 0; i < node->n_params; i++)
        {
          gchar *error;
          GType ptype = node->param_types[i] & ~G_SIGNAL_TYPE_STATIC_SCOPE;
          gboolean static_scope = node->param_types[i] & G_SIGNAL_TYPE_STATIC_SCOPE;

          SIGNAL_UNLOCK ();
          G_VALUE_COLLECT_INIT (param_values + i, ptype,
				var_args,
				static_scope ? G_VALUE_NOCOPY_CONTENTS : 0,
				&error);
          if (error)
            {
              g_warning ("%s: %s", G_STRLOC, error);
              g_free (error);

              /* we purposely leak the value here, it might not be
               * in a sane state if an error condition occoured
               */
              while (i--)
                g_value_unset (param_values + i);

              va_end (var_args);
              return;
            }
          SIGNAL_LOCK ();
        }

      SIGNAL_UNLOCK ();
      instance_and_params->g_type = 0;
      g_value_init_from_instance (instance_and_params, instance);
      SIGNAL_LOCK ();

      emission->chain_type = chain_type;
      SIGNAL_UNLOCK ();

      if (signal_return_type == G_TYPE_NONE)
        {
          g_closure_invoke (closure,
                            NULL,
                            n_params + 1,
                            instance_and_params,
                            &emission->ihint);
        }
      else
        {
          GValue return_value = G_VALUE_INIT;
          gchar *error = NULL;
          GType rtype = signal_return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE;
          gboolean static_scope = signal_return_type & G_SIGNAL_TYPE_STATIC_SCOPE;

          g_value_init (&return_value, rtype);

          g_closure_invoke (closure,
                            &return_value,
                            n_params + 1,
                            instance_and_params,
                            &emission->ihint);

          G_VALUE_LCOPY (&return_value,
                         var_args,
                         static_scope ? G_VALUE_NOCOPY_CONTENTS : 0,
                         &error);
          if (!error)
            {
              g_value_unset (&return_value);
            }
          else
            {
              g_warning ("%s: %s", G_STRLOC, error);
              g_free (error);

              /* we purposely leak the value here, it might not be
               * in a sane state if an error condition occurred
               */
            }
        }

      for (i = 0; i < n_params; i++)
        g_value_unset (param_values + i);
      g_value_unset (instance_and_params);

      va_end (var_args);

      SIGNAL_LOCK ();
      emission->chain_type = restore_type;
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_get_invocation_hint:
 * @instance: (type GObject.Object): the instance to query
 *
 * Returns the invocation hint of the innermost signal emission of instance.
 *
 * Returns: (transfer none): the invocation hint of the innermost signal  emission.
 */
GSignalInvocationHint*
g_signal_get_invocation_hint (gpointer instance)
{
  Emission *emission = NULL;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), NULL);

  SIGNAL_LOCK ();
  emission = emission_find_innermost (instance);
  SIGNAL_UNLOCK ();
  
  return emission ? &emission->ihint : NULL;
}

/**
 * g_signal_connect_closure_by_id:
 * @instance: (type GObject.Object): the instance to connect to.
 * @signal_id: the id of the signal.
 * @detail: the detail.
 * @closure: the closure to connect.
 * @after: whether the handler should be called before or after the
 *  default handler of the signal.
 *
 * Connects a closure to a signal for a particular object.
 *
 * Returns: the handler id (always greater than 0 for successful connections)
 */
gulong
g_signal_connect_closure_by_id (gpointer  instance,
				guint     signal_id,
				GQuark    detail,
				GClosure *closure,
				gboolean  after)
{
  SignalNode *node;
  gulong handler_seq_no = 0;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail (signal_id > 0, 0);
  g_return_val_if_fail (closure != NULL, 0);
  
  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (node)
    {
      if (detail && !(node->flags & G_SIGNAL_DETAILED))
	g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
      else if (!g_type_is_a (G_TYPE_FROM_INSTANCE (instance), node->itype))
	g_warning ("%s: signal id '%u' is invalid for instance '%p'", G_STRLOC, signal_id, instance);
      else
	{
	  Handler *handler = handler_new (after);
	  
	  handler_seq_no = handler->sequential_number;
	  handler->detail = detail;
	  handler->closure = g_closure_ref (closure);
	  g_closure_sink (closure);
	  add_invalid_closure_notify (handler, instance);
	  handler_insert (signal_id, instance, handler);
	  if (node->c_marshaller && G_CLOSURE_NEEDS_MARSHAL (closure))
	    {
	      g_closure_set_marshal (closure, node->c_marshaller);
	      if (node->va_marshaller)
		_g_closure_set_va_marshal (closure, node->va_marshaller);
	    }
	}
    }
  else
    g_warning ("%s: signal id '%u' is invalid for instance '%p'", G_STRLOC, signal_id, instance);
  SIGNAL_UNLOCK ();
  
  return handler_seq_no;
}

/**
 * g_signal_connect_closure:
 * @instance: (type GObject.Object): the instance to connect to.
 * @detailed_signal: a string of the form "signal-name::detail".
 * @closure: the closure to connect.
 * @after: whether the handler should be called before or after the
 *  default handler of the signal.
 *
 * Connects a closure to a signal for a particular object.
 *
 * Returns: the handler id (always greater than 0 for successful connections)
 */
gulong
g_signal_connect_closure (gpointer     instance,
			  const gchar *detailed_signal,
			  GClosure    *closure,
			  gboolean     after)
{
  guint signal_id;
  gulong handler_seq_no = 0;
  GQuark detail = 0;
  GType itype;

  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail (detailed_signal != NULL, 0);
  g_return_val_if_fail (closure != NULL, 0);

  SIGNAL_LOCK ();
  itype = G_TYPE_FROM_INSTANCE (instance);
  signal_id = signal_parse_name (detailed_signal, itype, &detail, TRUE);
  if (signal_id)
    {
      SignalNode *node = LOOKUP_SIGNAL_NODE (signal_id);

      if (detail && !(node->flags & G_SIGNAL_DETAILED))
	g_warning ("%s: signal '%s' does not support details", G_STRLOC, detailed_signal);
      else if (!g_type_is_a (itype, node->itype))
        g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
                   G_STRLOC, detailed_signal, instance, g_type_name (itype));
      else
	{
	  Handler *handler = handler_new (after);

	  handler_seq_no = handler->sequential_number;
	  handler->detail = detail;
	  handler->closure = g_closure_ref (closure);
	  g_closure_sink (closure);
	  add_invalid_closure_notify (handler, instance);
	  handler_insert (signal_id, instance, handler);
	  if (node->c_marshaller && G_CLOSURE_NEEDS_MARSHAL (handler->closure))
	    {
	      g_closure_set_marshal (handler->closure, node->c_marshaller);
	      if (node->va_marshaller)
		_g_closure_set_va_marshal (handler->closure, node->va_marshaller);
	    }
	}
    }
  else
    g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
               G_STRLOC, detailed_signal, instance, g_type_name (itype));
  SIGNAL_UNLOCK ();

  return handler_seq_no;
}

static void
node_check_deprecated (const SignalNode *node)
{
  static const gchar * g_enable_diagnostic = NULL;

  if (G_UNLIKELY (!g_enable_diagnostic))
    {
      g_enable_diagnostic = g_getenv ("G_ENABLE_DIAGNOSTIC");
      if (!g_enable_diagnostic)
        g_enable_diagnostic = "0";
    }

  if (g_enable_diagnostic[0] == '1')
    {
      if (node->flags & G_SIGNAL_DEPRECATED)
        {
          g_warning ("The signal %s::%s is deprecated and shouldn't be used "
                     "anymore. It will be removed in a future version.",
                     type_debug_name (node->itype), node->name);
        }
    }
}

/**
 * g_signal_connect_data:
 * @instance: (type GObject.Object): the instance to connect to.
 * @detailed_signal: a string of the form "signal-name::detail".
 * @c_handler: the #GCallback to connect.
 * @data: data to pass to @c_handler calls.
 * @destroy_data: a #GClosureNotify for @data.
 * @connect_flags: a combination of #GConnectFlags.
 *
 * Connects a #GCallback function to a signal for a particular object. Similar
 * to g_signal_connect(), but allows to provide a #GClosureNotify for the data
 * which will be called when the signal handler is disconnected and no longer
 * used. Specify @connect_flags if you need `..._after()` or
 * `..._swapped()` variants of this function.
 *
 * Returns: the handler id (always greater than 0 for successful connections)
 */
gulong
g_signal_connect_data (gpointer       instance,
		       const gchar   *detailed_signal,
		       GCallback      c_handler,
		       gpointer       data,
		       GClosureNotify destroy_data,
		       GConnectFlags  connect_flags)
{
  guint signal_id;
  gulong handler_seq_no = 0;
  GQuark detail = 0;
  GType itype;
  gboolean swapped, after;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail (detailed_signal != NULL, 0);
  g_return_val_if_fail (c_handler != NULL, 0);

  swapped = (connect_flags & G_CONNECT_SWAPPED) != FALSE;
  after = (connect_flags & G_CONNECT_AFTER) != FALSE;

  SIGNAL_LOCK ();
  itype = G_TYPE_FROM_INSTANCE (instance);
  signal_id = signal_parse_name (detailed_signal, itype, &detail, TRUE);
  if (signal_id)
    {
      SignalNode *node = LOOKUP_SIGNAL_NODE (signal_id);

      node_check_deprecated (node);

      if (detail && !(node->flags & G_SIGNAL_DETAILED))
	g_warning ("%s: signal '%s' does not support details", G_STRLOC, detailed_signal);
      else if (!g_type_is_a (itype, node->itype))
        g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
                   G_STRLOC, detailed_signal, instance, g_type_name (itype));
      else
	{
	  Handler *handler = handler_new (after);

	  handler_seq_no = handler->sequential_number;
	  handler->detail = detail;
	  handler->closure = g_closure_ref ((swapped ? g_cclosure_new_swap : g_cclosure_new) (c_handler, data, destroy_data));
	  g_closure_sink (handler->closure);
	  handler_insert (signal_id, instance, handler);
	  if (node->c_marshaller && G_CLOSURE_NEEDS_MARSHAL (handler->closure))
	    {
	      g_closure_set_marshal (handler->closure, node->c_marshaller);
	      if (node->va_marshaller)
		_g_closure_set_va_marshal (handler->closure, node->va_marshaller);
	    }
        }
    }
  else
    g_warning ("%s: signal '%s' is invalid for instance '%p' of type '%s'",
               G_STRLOC, detailed_signal, instance, g_type_name (itype));
  SIGNAL_UNLOCK ();

  return handler_seq_no;
}

/**
 * g_signal_handler_block:
 * @instance: (type GObject.Object): The instance to block the signal handler of.
 * @handler_id: Handler id of the handler to be blocked.
 *
 * Blocks a handler of an instance so it will not be called during any
 * signal emissions unless it is unblocked again. Thus "blocking" a
 * signal handler means to temporarily deactive it, a signal handler
 * has to be unblocked exactly the same amount of times it has been
 * blocked before to become active again.
 *
 * The @handler_id has to be a valid signal handler id, connected to a
 * signal of @instance.
 */
void
g_signal_handler_block (gpointer instance,
                        gulong   handler_id)
{
  Handler *handler;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (handler_id > 0);
  
  SIGNAL_LOCK ();
  handler = handler_lookup (instance, handler_id, NULL, NULL);
  if (handler)
    {
#ifndef G_DISABLE_CHECKS
      if (handler->block_count >= HANDLER_MAX_BLOCK_COUNT - 1)
        g_error (G_STRLOC ": handler block_count overflow, %s", REPORT_BUG);
#endif
      handler->block_count += 1;
    }
  else
    g_warning ("%s: instance '%p' has no handler with id '%lu'", G_STRLOC, instance, handler_id);
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_handler_unblock:
 * @instance: (type GObject.Object): The instance to unblock the signal handler of.
 * @handler_id: Handler id of the handler to be unblocked.
 *
 * Undoes the effect of a previous g_signal_handler_block() call.  A
 * blocked handler is skipped during signal emissions and will not be
 * invoked, unblocking it (for exactly the amount of times it has been
 * blocked before) reverts its "blocked" state, so the handler will be
 * recognized by the signal system and is called upon future or
 * currently ongoing signal emissions (since the order in which
 * handlers are called during signal emissions is deterministic,
 * whether the unblocked handler in question is called as part of a
 * currently ongoing emission depends on how far that emission has
 * proceeded yet).
 *
 * The @handler_id has to be a valid id of a signal handler that is
 * connected to a signal of @instance and is currently blocked.
 */
void
g_signal_handler_unblock (gpointer instance,
                          gulong   handler_id)
{
  Handler *handler;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (handler_id > 0);
  
  SIGNAL_LOCK ();
  handler = handler_lookup (instance, handler_id, NULL, NULL);
  if (handler)
    {
      if (handler->block_count)
        handler->block_count -= 1;
      else
        g_warning (G_STRLOC ": handler '%lu' of instance '%p' is not blocked", handler_id, instance);
    }
  else
    g_warning ("%s: instance '%p' has no handler with id '%lu'", G_STRLOC, instance, handler_id);
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_handler_disconnect:
 * @instance: (type GObject.Object): The instance to remove the signal handler from.
 * @handler_id: Handler id of the handler to be disconnected.
 *
 * Disconnects a handler from an instance so it will not be called during
 * any future or currently ongoing emissions of the signal it has been
 * connected to. The @handler_id becomes invalid and may be reused.
 *
 * The @handler_id has to be a valid signal handler id, connected to a
 * signal of @instance.
 */
void
g_signal_handler_disconnect (gpointer instance,
                             gulong   handler_id)
{
  Handler *handler;
  guint signal_id;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (handler_id > 0);
  
  SIGNAL_LOCK ();
  handler = handler_lookup (instance, handler_id, NULL, &signal_id);
  if (handler)
    {
      handler->sequential_number = 0;
      handler->block_count = 1;
      remove_invalid_closure_notify (handler, instance);
      handler_unref_R (signal_id, instance, handler);
    }
  else
    g_warning ("%s: instance '%p' has no handler with id '%lu'", G_STRLOC, instance, handler_id);
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_handler_is_connected:
 * @instance: (type GObject.Object): The instance where a signal handler is sought.
 * @handler_id: the handler id.
 *
 * Returns whether @handler_id is the id of a handler connected to @instance.
 *
 * Returns: whether @handler_id identifies a handler connected to @instance.
 */
gboolean
g_signal_handler_is_connected (gpointer instance,
			       gulong   handler_id)
{
  Handler *handler;
  gboolean connected;

  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), FALSE);

  SIGNAL_LOCK ();
  handler = handler_lookup (instance, handler_id, NULL, NULL);
  connected = handler != NULL;
  SIGNAL_UNLOCK ();

  return connected;
}

/**
 * g_signal_handlers_destroy:
 * @instance: (type GObject.Object): The instance whose signal handlers are destroyed
 *
 * Destroy all signal handlers of a type instance. This function is
 * an implementation detail of the #GObject dispose implementation,
 * and should not be used outside of the type system.
 */
void
g_signal_handlers_destroy (gpointer instance)
{
  GBSearchArray *hlbsa;
  
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  
  SIGNAL_LOCK ();
  hlbsa = g_hash_table_lookup (g_handler_list_bsa_ht, instance);
  if (hlbsa)
    {
      guint i;
      
      /* reentrancy caution, delete instance trace first */
      g_hash_table_remove (g_handler_list_bsa_ht, instance);
      
      for (i = 0; i < hlbsa->n_nodes; i++)
        {
          HandlerList *hlist = g_bsearch_array_get_nth (hlbsa, &g_signal_hlbsa_bconfig, i);
          Handler *handler = hlist->handlers;
	  
          while (handler)
            {
              Handler *tmp = handler;
	      
              handler = tmp->next;
              tmp->block_count = 1;
              /* cruel unlink, this works because _all_ handlers vanish */
              tmp->next = NULL;
              tmp->prev = tmp;
              if (tmp->sequential_number)
		{
		  remove_invalid_closure_notify (tmp, instance);
		  tmp->sequential_number = 0;
		  handler_unref_R (0, NULL, tmp);
		}
            }
        }
      g_bsearch_array_free (hlbsa, &g_signal_hlbsa_bconfig);
    }
  SIGNAL_UNLOCK ();
}

/**
 * g_signal_handler_find:
 * @instance: (type GObject.Object): The instance owning the signal handler to be found.
 * @mask: Mask indicating which of @signal_id, @detail, @closure, @func
 *  and/or @data the handler has to match.
 * @signal_id: Signal the handler has to be connected to.
 * @detail: Signal detail the handler has to be connected to.
 * @closure: (allow-none): The closure the handler will invoke.
 * @func: The C closure callback of the handler (useless for non-C closures).
 * @data: The closure data of the handler's closure.
 *
 * Finds the first signal handler that matches certain selection criteria.
 * The criteria mask is passed as an OR-ed combination of #GSignalMatchType
 * flags, and the criteria values are passed as arguments.
 * The match @mask has to be non-0 for successful matches.
 * If no handler was found, 0 is returned.
 *
 * Returns: A valid non-0 signal handler id for a successful match.
 */
gulong
g_signal_handler_find (gpointer         instance,
                       GSignalMatchType mask,
                       guint            signal_id,
		       GQuark		detail,
                       GClosure        *closure,
                       gpointer         func,
                       gpointer         data)
{
  gulong handler_seq_no = 0;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail ((mask & ~G_SIGNAL_MATCH_MASK) == 0, 0);
  
  if (mask & G_SIGNAL_MATCH_MASK)
    {
      HandlerMatch *mlist;
      
      SIGNAL_LOCK ();
      mlist = handlers_find (instance, mask, signal_id, detail, closure, func, data, TRUE);
      if (mlist)
	{
	  handler_seq_no = mlist->handler->sequential_number;
	  handler_match_free1_R (mlist, instance);
	}
      SIGNAL_UNLOCK ();
    }
  
  return handler_seq_no;
}

static guint
signal_handlers_foreach_matched_R (gpointer         instance,
				   GSignalMatchType mask,
				   guint            signal_id,
				   GQuark           detail,
				   GClosure        *closure,
				   gpointer         func,
				   gpointer         data,
				   void		  (*callback) (gpointer instance,
							       gulong   handler_seq_no))
{
  HandlerMatch *mlist;
  guint n_handlers = 0;
  
  mlist = handlers_find (instance, mask, signal_id, detail, closure, func, data, FALSE);
  while (mlist)
    {
      n_handlers++;
      if (mlist->handler->sequential_number)
	{
	  SIGNAL_UNLOCK ();
	  callback (instance, mlist->handler->sequential_number);
	  SIGNAL_LOCK ();
	}
      mlist = handler_match_free1_R (mlist, instance);
    }
  
  return n_handlers;
}

/**
 * g_signal_handlers_block_matched:
 * @instance: (type GObject.Object): The instance to block handlers from.
 * @mask: Mask indicating which of @signal_id, @detail, @closure, @func
 *  and/or @data the handlers have to match.
 * @signal_id: Signal the handlers have to be connected to.
 * @detail: Signal detail the handlers have to be connected to.
 * @closure: (allow-none): The closure the handlers will invoke.
 * @func: The C closure callback of the handlers (useless for non-C closures).
 * @data: The closure data of the handlers' closures.
 *
 * Blocks all handlers on an instance that match a certain selection criteria.
 * The criteria mask is passed as an OR-ed combination of #GSignalMatchType
 * flags, and the criteria values are passed as arguments.
 * Passing at least one of the %G_SIGNAL_MATCH_CLOSURE, %G_SIGNAL_MATCH_FUNC
 * or %G_SIGNAL_MATCH_DATA match flags is required for successful matches.
 * If no handlers were found, 0 is returned, the number of blocked handlers
 * otherwise.
 *
 * Returns: The number of handlers that matched.
 */
guint
g_signal_handlers_block_matched (gpointer         instance,
				 GSignalMatchType mask,
				 guint            signal_id,
				 GQuark           detail,
				 GClosure        *closure,
				 gpointer         func,
				 gpointer         data)
{
  guint n_handlers = 0;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail ((mask & ~G_SIGNAL_MATCH_MASK) == 0, 0);
  
  if (mask & (G_SIGNAL_MATCH_CLOSURE | G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA))
    {
      SIGNAL_LOCK ();
      n_handlers = signal_handlers_foreach_matched_R (instance, mask, signal_id, detail,
						      closure, func, data,
						      g_signal_handler_block);
      SIGNAL_UNLOCK ();
    }
  
  return n_handlers;
}

/**
 * g_signal_handlers_unblock_matched:
 * @instance: (type GObject.Object): The instance to unblock handlers from.
 * @mask: Mask indicating which of @signal_id, @detail, @closure, @func
 *  and/or @data the handlers have to match.
 * @signal_id: Signal the handlers have to be connected to.
 * @detail: Signal detail the handlers have to be connected to.
 * @closure: (allow-none): The closure the handlers will invoke.
 * @func: The C closure callback of the handlers (useless for non-C closures).
 * @data: The closure data of the handlers' closures.
 *
 * Unblocks all handlers on an instance that match a certain selection
 * criteria. The criteria mask is passed as an OR-ed combination of
 * #GSignalMatchType flags, and the criteria values are passed as arguments.
 * Passing at least one of the %G_SIGNAL_MATCH_CLOSURE, %G_SIGNAL_MATCH_FUNC
 * or %G_SIGNAL_MATCH_DATA match flags is required for successful matches.
 * If no handlers were found, 0 is returned, the number of unblocked handlers
 * otherwise. The match criteria should not apply to any handlers that are
 * not currently blocked.
 *
 * Returns: The number of handlers that matched.
 */
guint
g_signal_handlers_unblock_matched (gpointer         instance,
				   GSignalMatchType mask,
				   guint            signal_id,
				   GQuark           detail,
				   GClosure        *closure,
				   gpointer         func,
				   gpointer         data)
{
  guint n_handlers = 0;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail ((mask & ~G_SIGNAL_MATCH_MASK) == 0, 0);
  
  if (mask & (G_SIGNAL_MATCH_CLOSURE | G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA))
    {
      SIGNAL_LOCK ();
      n_handlers = signal_handlers_foreach_matched_R (instance, mask, signal_id, detail,
						      closure, func, data,
						      g_signal_handler_unblock);
      SIGNAL_UNLOCK ();
    }
  
  return n_handlers;
}

/**
 * g_signal_handlers_disconnect_matched:
 * @instance: (type GObject.Object): The instance to remove handlers from.
 * @mask: Mask indicating which of @signal_id, @detail, @closure, @func
 *  and/or @data the handlers have to match.
 * @signal_id: Signal the handlers have to be connected to.
 * @detail: Signal detail the handlers have to be connected to.
 * @closure: (allow-none): The closure the handlers will invoke.
 * @func: The C closure callback of the handlers (useless for non-C closures).
 * @data: The closure data of the handlers' closures.
 *
 * Disconnects all handlers on an instance that match a certain
 * selection criteria. The criteria mask is passed as an OR-ed
 * combination of #GSignalMatchType flags, and the criteria values are
 * passed as arguments.  Passing at least one of the
 * %G_SIGNAL_MATCH_CLOSURE, %G_SIGNAL_MATCH_FUNC or
 * %G_SIGNAL_MATCH_DATA match flags is required for successful
 * matches.  If no handlers were found, 0 is returned, the number of
 * disconnected handlers otherwise.
 *
 * Returns: The number of handlers that matched.
 */
guint
g_signal_handlers_disconnect_matched (gpointer         instance,
				      GSignalMatchType mask,
				      guint            signal_id,
				      GQuark           detail,
				      GClosure        *closure,
				      gpointer         func,
				      gpointer         data)
{
  guint n_handlers = 0;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), 0);
  g_return_val_if_fail ((mask & ~G_SIGNAL_MATCH_MASK) == 0, 0);
  
  if (mask & (G_SIGNAL_MATCH_CLOSURE | G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA))
    {
      SIGNAL_LOCK ();
      n_handlers = signal_handlers_foreach_matched_R (instance, mask, signal_id, detail,
						      closure, func, data,
						      g_signal_handler_disconnect);
      SIGNAL_UNLOCK ();
    }
  
  return n_handlers;
}

/**
 * g_signal_has_handler_pending:
 * @instance: (type GObject.Object): the object whose signal handlers are sought.
 * @signal_id: the signal id.
 * @detail: the detail.
 * @may_be_blocked: whether blocked handlers should count as match.
 *
 * Returns whether there are any handlers connected to @instance for the
 * given signal id and detail.
 *
 * One example of when you might use this is when the arguments to the
 * signal are difficult to compute. A class implementor may opt to not
 * emit the signal if no one is attached anyway, thus saving the cost
 * of building the arguments.
 *
 * Returns: %TRUE if a handler is connected to the signal, %FALSE
 *          otherwise.
 */
gboolean
g_signal_has_handler_pending (gpointer instance,
			      guint    signal_id,
			      GQuark   detail,
			      gboolean may_be_blocked)
{
  HandlerMatch *mlist;
  gboolean has_pending;
  
  g_return_val_if_fail (G_TYPE_CHECK_INSTANCE (instance), FALSE);
  g_return_val_if_fail (signal_id > 0, FALSE);
  
  SIGNAL_LOCK ();
  if (detail)
    {
      SignalNode *node = LOOKUP_SIGNAL_NODE (signal_id);
      
      if (!(node->flags & G_SIGNAL_DETAILED))
	{
	  g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
	  SIGNAL_UNLOCK ();
	  return FALSE;
	}
    }
  mlist = handlers_find (instance,
			 (G_SIGNAL_MATCH_ID | G_SIGNAL_MATCH_DETAIL | (may_be_blocked ? 0 : G_SIGNAL_MATCH_UNBLOCKED)),
			 signal_id, detail, NULL, NULL, NULL, TRUE);
  if (mlist)
    {
      has_pending = TRUE;
      handler_match_free1_R (mlist, instance);
    }
  else
    has_pending = FALSE;
  SIGNAL_UNLOCK ();
  
  return has_pending;
}

/**
 * g_signal_emitv:
 * @instance_and_params: (array): argument list for the signal emission.
 *  The first element in the array is a #GValue for the instance the signal
 *  is being emitted on. The rest are any arguments to be passed to the signal.
 * @signal_id: the signal id
 * @detail: the detail
 * @return_value: Location to store the return value of the signal emission.
 *
 * Emits a signal.
 *
 * Note that g_signal_emitv() doesn't change @return_value if no handlers are
 * connected, in contrast to g_signal_emit() and g_signal_emit_valist().
 */
void
g_signal_emitv (const GValue *instance_and_params,
		guint         signal_id,
		GQuark	      detail,
		GValue       *return_value)
{
  gpointer instance;
  SignalNode *node;
#ifdef G_ENABLE_DEBUG
  const GValue *param_values;
  guint i;
#endif
  
  g_return_if_fail (instance_and_params != NULL);
  instance = g_value_peek_pointer (instance_and_params);
  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (signal_id > 0);

#ifdef G_ENABLE_DEBUG
  param_values = instance_and_params + 1;
#endif

  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (!node || !g_type_is_a (G_TYPE_FROM_INSTANCE (instance), node->itype))
    {
      g_warning ("%s: signal id '%u' is invalid for instance '%p'", G_STRLOC, signal_id, instance);
      SIGNAL_UNLOCK ();
      return;
    }
#ifdef G_ENABLE_DEBUG
  if (detail && !(node->flags & G_SIGNAL_DETAILED))
    {
      g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
      SIGNAL_UNLOCK ();
      return;
    }
  for (i = 0; i < node->n_params; i++)
    if (!G_TYPE_CHECK_VALUE_TYPE (param_values + i, node->param_types[i] & ~G_SIGNAL_TYPE_STATIC_SCOPE))
      {
	g_critical ("%s: value for '%s' parameter %u for signal \"%s\" is of type '%s'",
		    G_STRLOC,
		    type_debug_name (node->param_types[i]),
		    i,
		    node->name,
		    G_VALUE_TYPE_NAME (param_values + i));
	SIGNAL_UNLOCK ();
	return;
      }
  if (node->return_type != G_TYPE_NONE)
    {
      if (!return_value)
	{
	  g_critical ("%s: return value '%s' for signal \"%s\" is (NULL)",
		      G_STRLOC,
		      type_debug_name (node->return_type),
		      node->name);
	  SIGNAL_UNLOCK ();
	  return;
	}
      else if (!node->accumulator && !G_TYPE_CHECK_VALUE_TYPE (return_value, node->return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE))
	{
	  g_critical ("%s: return value '%s' for signal \"%s\" is of type '%s'",
		      G_STRLOC,
		      type_debug_name (node->return_type),
		      node->name,
		      G_VALUE_TYPE_NAME (return_value));
	  SIGNAL_UNLOCK ();
	  return;
	}
    }
  else
    return_value = NULL;
#endif	/* G_ENABLE_DEBUG */

  /* optimize NOP emissions */
  if (!node->single_va_closure_is_valid)
    node_update_single_va_closure (node);

  if (node->single_va_closure != NULL &&
      (node->single_va_closure == SINGLE_VA_CLOSURE_EMPTY_MAGIC ||
       _g_closure_is_void (node->single_va_closure, instance)))
    {
      HandlerList* hlist = handler_list_lookup (node->signal_id, instance);
      if (hlist == NULL || hlist->handlers == NULL)
	{
	  /* nothing to do to emit this signal */
	  SIGNAL_UNLOCK ();
	  /* g_printerr ("omitting emission of \"%s\"\n", node->name); */
	  return;
	}
    }

  SIGNAL_UNLOCK ();
  signal_emit_unlocked_R (node, detail, instance, return_value, instance_and_params);
}

static inline gboolean
accumulate (GSignalInvocationHint *ihint,
	    GValue                *return_accu,
	    GValue	          *handler_return,
	    SignalAccumulator     *accumulator)
{
  gboolean continue_emission;

  if (!accumulator)
    return TRUE;

  continue_emission = accumulator->func (ihint, return_accu, handler_return, accumulator->data);
  g_value_reset (handler_return);

  return continue_emission;
}

/**
 * g_signal_emit_valist: (skip)
 * @instance: the instance the signal is being emitted on.
 * @signal_id: the signal id
 * @detail: the detail
 * @var_args: a list of parameters to be passed to the signal, followed by a
 *  location for the return value. If the return type of the signal
 *  is #G_TYPE_NONE, the return value location can be omitted.
 *
 * Emits a signal.
 *
 * Note that g_signal_emit_valist() resets the return value to the default
 * if no handlers are connected, in contrast to g_signal_emitv().
 */
void
g_signal_emit_valist (gpointer instance,
		      guint    signal_id,
		      GQuark   detail,
		      va_list  var_args)
{
  GValue *instance_and_params;
  GType signal_return_type;
  GValue *param_values;
  SignalNode *node;
  guint i, n_params;

  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (signal_id > 0);

  SIGNAL_LOCK ();
  node = LOOKUP_SIGNAL_NODE (signal_id);
  if (!node || !g_type_is_a (G_TYPE_FROM_INSTANCE (instance), node->itype))
    {
      g_warning ("%s: signal id '%u' is invalid for instance '%p'", G_STRLOC, signal_id, instance);
      SIGNAL_UNLOCK ();
      return;
    }
#ifndef G_DISABLE_CHECKS
  if (detail && !(node->flags & G_SIGNAL_DETAILED))
    {
      g_warning ("%s: signal id '%u' does not support detail (%u)", G_STRLOC, signal_id, detail);
      SIGNAL_UNLOCK ();
      return;
    }
#endif  /* !G_DISABLE_CHECKS */

  if (!node->single_va_closure_is_valid)
    node_update_single_va_closure (node);

  if (node->single_va_closure != NULL)
    {
      HandlerList* hlist = handler_list_lookup (node->signal_id, instance);
      Handler *fastpath_handler = NULL;
      Handler *l;
      GClosure *closure = NULL;
      gboolean fastpath = TRUE;
      GSignalFlags run_type = G_SIGNAL_RUN_FIRST;

      if (node->single_va_closure != SINGLE_VA_CLOSURE_EMPTY_MAGIC &&
	  !_g_closure_is_void (node->single_va_closure, instance))
	{
	  if (_g_closure_supports_invoke_va (node->single_va_closure))
	    {
	      closure = node->single_va_closure;
	      if (node->single_va_closure_is_after)
		run_type = G_SIGNAL_RUN_LAST;
	      else
		run_type = G_SIGNAL_RUN_FIRST;
	    }
	  else
	    fastpath = FALSE;
	}

      for (l = hlist ? hlist->handlers : NULL; fastpath && l != NULL; l = l->next)
	{
	  if (!l->block_count &&
	      (!l->detail || l->detail == detail))
	    {
	      if (closure != NULL || !_g_closure_supports_invoke_va (l->closure))
		{
		  fastpath = FALSE;
		  break;
		}
	      else
		{
                  fastpath_handler = l;
		  closure = l->closure;
		  if (l->after)
		    run_type = G_SIGNAL_RUN_LAST;
		  else
		    run_type = G_SIGNAL_RUN_FIRST;
		}
	    }
	}

      if (fastpath && closure == NULL && node->return_type == G_TYPE_NONE)
	{
	  SIGNAL_UNLOCK ();
	  return;
	}

      /* Don't allow no-recurse emission as we might have to restart, which means
	 we will run multiple handlers and thus must ref all arguments */
      if (closure != NULL && (node->flags & (G_SIGNAL_NO_RECURSE)) != 0)
	fastpath = FALSE;
      
      if (fastpath)
	{
	  SignalAccumulator *accumulator;
	  Emission emission;
	  GValue *return_accu, accu = G_VALUE_INIT;
	  guint signal_id;
	  GType instance_type = G_TYPE_FROM_INSTANCE (instance);
	  GValue emission_return = G_VALUE_INIT;
          GType rtype = node->return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE;
	  gboolean static_scope = node->return_type & G_SIGNAL_TYPE_STATIC_SCOPE;

	  signal_id = node->signal_id;
	  accumulator = node->accumulator;
	  if (rtype == G_TYPE_NONE)
	    return_accu = NULL;
	  else if (accumulator)
	    return_accu = &accu;
	  else
	    return_accu = &emission_return;

	  emission.instance = instance;
	  emission.ihint.signal_id = signal_id;
	  emission.ihint.detail = detail;
	  emission.ihint.run_type = run_type;
	  emission.state = EMISSION_RUN;
	  emission.chain_type = instance_type;
	  emission_push (&g_recursive_emissions, &emission);

          if (fastpath_handler)
            handler_ref (fastpath_handler);

	  SIGNAL_UNLOCK ();

	  TRACE(GOBJECT_SIGNAL_EMIT(signal_id, detail, instance, instance_type));

	  if (rtype != G_TYPE_NONE)
	    g_value_init (&emission_return, rtype);

	  if (accumulator)
	    g_value_init (&accu, rtype);

	  if (closure != NULL)
	    {
	      g_object_ref (instance);
	      _g_closure_invoke_va (closure,
				    return_accu,
				    instance,
				    var_args,
				    node->n_params,
				    node->param_types);
	      accumulate (&emission.ihint, &emission_return, &accu, accumulator);
	    }

	  SIGNAL_LOCK ();

	  emission.chain_type = G_TYPE_NONE;
	  emission_pop (&g_recursive_emissions, &emission);

          if (fastpath_handler)
            handler_unref_R (signal_id, instance, fastpath_handler);

	  SIGNAL_UNLOCK ();

	  if (accumulator)
	    g_value_unset (&accu);

	  if (rtype != G_TYPE_NONE)
	    {
	      gchar *error = NULL;
	      for (i = 0; i < node->n_params; i++)
		{
		  GType ptype = node->param_types[i] & ~G_SIGNAL_TYPE_STATIC_SCOPE;
		  G_VALUE_COLLECT_SKIP (ptype, var_args);
		}

	      G_VALUE_LCOPY (&emission_return,
			     var_args,
			     static_scope ? G_VALUE_NOCOPY_CONTENTS : 0,
			     &error);
	      if (!error)
		g_value_unset (&emission_return);
	      else
		{
		  g_warning ("%s: %s", G_STRLOC, error);
		  g_free (error);
		  /* we purposely leak the value here, it might not be
		   * in a sane state if an error condition occurred
		   */
		}
	    }
	  
	  TRACE(GOBJECT_SIGNAL_EMIT_END(signal_id, detail, instance, instance_type));

          if (closure != NULL)
            g_object_unref (instance);

	  return;
	}
    }
  SIGNAL_UNLOCK ();

  n_params = node->n_params;
  signal_return_type = node->return_type;
  instance_and_params = g_alloca (sizeof (GValue) * (n_params + 1));
  memset (instance_and_params, 0, sizeof (GValue) * (n_params + 1));
  param_values = instance_and_params + 1;

  for (i = 0; i < node->n_params; i++)
    {
      gchar *error;
      GType ptype = node->param_types[i] & ~G_SIGNAL_TYPE_STATIC_SCOPE;
      gboolean static_scope = node->param_types[i] & G_SIGNAL_TYPE_STATIC_SCOPE;

      G_VALUE_COLLECT_INIT (param_values + i, ptype,
			    var_args,
			    static_scope ? G_VALUE_NOCOPY_CONTENTS : 0,
			    &error);
      if (error)
	{
	  g_warning ("%s: %s", G_STRLOC, error);
	  g_free (error);

	  /* we purposely leak the value here, it might not be
	   * in a sane state if an error condition occoured
	   */
	  while (i--)
	    g_value_unset (param_values + i);

	  return;
	}
    }

  instance_and_params->g_type = 0;
  g_value_init_from_instance (instance_and_params, instance);
  if (signal_return_type == G_TYPE_NONE)
    signal_emit_unlocked_R (node, detail, instance, NULL, instance_and_params);
  else
    {
      GValue return_value = G_VALUE_INIT;
      gchar *error = NULL;
      GType rtype = signal_return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE;
      gboolean static_scope = signal_return_type & G_SIGNAL_TYPE_STATIC_SCOPE;
      
      g_value_init (&return_value, rtype);

      signal_emit_unlocked_R (node, detail, instance, &return_value, instance_and_params);

      G_VALUE_LCOPY (&return_value,
		     var_args,
		     static_scope ? G_VALUE_NOCOPY_CONTENTS : 0,
		     &error);
      if (!error)
	g_value_unset (&return_value);
      else
	{
	  g_warning ("%s: %s", G_STRLOC, error);
	  g_free (error);
	  
	  /* we purposely leak the value here, it might not be
	   * in a sane state if an error condition occurred
	   */
	}
    }
  for (i = 0; i < n_params; i++)
    g_value_unset (param_values + i);
  g_value_unset (instance_and_params);
}

/**
 * g_signal_emit:
 * @instance: (type GObject.Object): the instance the signal is being emitted on.
 * @signal_id: the signal id
 * @detail: the detail
 * @...: parameters to be passed to the signal, followed by a
 *  location for the return value. If the return type of the signal
 *  is #G_TYPE_NONE, the return value location can be omitted.
 *
 * Emits a signal.
 *
 * Note that g_signal_emit() resets the return value to the default
 * if no handlers are connected, in contrast to g_signal_emitv().
 */
void
g_signal_emit (gpointer instance,
	       guint    signal_id,
	       GQuark   detail,
	       ...)
{
  va_list var_args;

  va_start (var_args, detail);
  g_signal_emit_valist (instance, signal_id, detail, var_args);
  va_end (var_args);
}

/**
 * g_signal_emit_by_name:
 * @instance: (type GObject.Object): the instance the signal is being emitted on.
 * @detailed_signal: a string of the form "signal-name::detail".
 * @...: parameters to be passed to the signal, followed by a
 *  location for the return value. If the return type of the signal
 *  is #G_TYPE_NONE, the return value location can be omitted.
 *
 * Emits a signal.
 *
 * Note that g_signal_emit_by_name() resets the return value to the default
 * if no handlers are connected, in contrast to g_signal_emitv().
 */
void
g_signal_emit_by_name (gpointer     instance,
		       const gchar *detailed_signal,
		       ...)
{
  GQuark detail = 0;
  guint signal_id;
  GType itype;

  g_return_if_fail (G_TYPE_CHECK_INSTANCE (instance));
  g_return_if_fail (detailed_signal != NULL);

  itype = G_TYPE_FROM_INSTANCE (instance);

  SIGNAL_LOCK ();
  signal_id = signal_parse_name (detailed_signal, itype, &detail, TRUE);
  SIGNAL_UNLOCK ();

  if (signal_id)
    {
      va_list var_args;

      va_start (var_args, detailed_signal);
      g_signal_emit_valist (instance, signal_id, detail, var_args);
      va_end (var_args);
    }
  else
    g_warning ("%s: signal name '%s' is invalid for instance '%p' of type '%s'",
               G_STRLOC, detailed_signal, instance, g_type_name (itype));
}

static gboolean
signal_emit_unlocked_R (SignalNode   *node,
			GQuark	      detail,
			gpointer      instance,
			GValue	     *emission_return,
			const GValue *instance_and_params)
{
  SignalAccumulator *accumulator;
  Emission emission;
  GClosure *class_closure;
  HandlerList *hlist;
  Handler *handler_list = NULL;
  GValue *return_accu, accu = G_VALUE_INIT;
  guint signal_id;
  gulong max_sequential_handler_number;
  gboolean return_value_altered = FALSE;
  
  TRACE(GOBJECT_SIGNAL_EMIT(node->signal_id, detail, instance, G_TYPE_FROM_INSTANCE (instance)));

  SIGNAL_LOCK ();
  signal_id = node->signal_id;

  if (node->flags & G_SIGNAL_NO_RECURSE)
    {
      Emission *node = emission_find (g_restart_emissions, signal_id, detail, instance);
      
      if (node)
	{
	  node->state = EMISSION_RESTART;
	  SIGNAL_UNLOCK ();
	  return return_value_altered;
	}
    }
  accumulator = node->accumulator;
  if (accumulator)
    {
      SIGNAL_UNLOCK ();
      g_value_init (&accu, node->return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE);
      return_accu = &accu;
      SIGNAL_LOCK ();
    }
  else
    return_accu = emission_return;
  emission.instance = instance;
  emission.ihint.signal_id = node->signal_id;
  emission.ihint.detail = detail;
  emission.ihint.run_type = 0;
  emission.state = 0;
  emission.chain_type = G_TYPE_NONE;
  emission_push ((node->flags & G_SIGNAL_NO_RECURSE) ? &g_restart_emissions : &g_recursive_emissions, &emission);
  class_closure = signal_lookup_closure (node, instance);
  
 EMIT_RESTART:
  
  if (handler_list)
    handler_unref_R (signal_id, instance, handler_list);
  max_sequential_handler_number = g_handler_sequential_number;
  hlist = handler_list_lookup (signal_id, instance);
  handler_list = hlist ? hlist->handlers : NULL;
  if (handler_list)
    handler_ref (handler_list);
  
  emission.ihint.run_type = G_SIGNAL_RUN_FIRST;
  
  if ((node->flags & G_SIGNAL_RUN_FIRST) && class_closure)
    {
      emission.state = EMISSION_RUN;

      emission.chain_type = G_TYPE_FROM_INSTANCE (instance);
      SIGNAL_UNLOCK ();
      g_closure_invoke (class_closure,
			return_accu,
			node->n_params + 1,
			instance_and_params,
			&emission.ihint);
      if (!accumulate (&emission.ihint, emission_return, &accu, accumulator) &&
	  emission.state == EMISSION_RUN)
	emission.state = EMISSION_STOP;
      SIGNAL_LOCK ();
      emission.chain_type = G_TYPE_NONE;
      return_value_altered = TRUE;
      
      if (emission.state == EMISSION_STOP)
	goto EMIT_CLEANUP;
      else if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
  if (node->emission_hooks)
    {
      gboolean need_destroy, was_in_call, may_recurse = TRUE;
      GHook *hook;

      emission.state = EMISSION_HOOK;
      hook = g_hook_first_valid (node->emission_hooks, may_recurse);
      while (hook)
	{
	  SignalHook *signal_hook = SIGNAL_HOOK (hook);
	  
	  if (!signal_hook->detail || signal_hook->detail == detail)
	    {
	      GSignalEmissionHook hook_func = (GSignalEmissionHook) hook->func;
	      
	      was_in_call = G_HOOK_IN_CALL (hook);
	      hook->flags |= G_HOOK_FLAG_IN_CALL;
              SIGNAL_UNLOCK ();
	      need_destroy = !hook_func (&emission.ihint, node->n_params + 1, instance_and_params, hook->data);
	      SIGNAL_LOCK ();
	      if (!was_in_call)
		hook->flags &= ~G_HOOK_FLAG_IN_CALL;
	      if (need_destroy)
		g_hook_destroy_link (node->emission_hooks, hook);
	    }
	  hook = g_hook_next_valid (node->emission_hooks, hook, may_recurse);
	}
      
      if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
  if (handler_list)
    {
      Handler *handler = handler_list;
      
      emission.state = EMISSION_RUN;
      handler_ref (handler);
      do
	{
	  Handler *tmp;
	  
	  if (handler->after)
	    {
	      handler_unref_R (signal_id, instance, handler_list);
	      handler_list = handler;
	      break;
	    }
	  else if (!handler->block_count && (!handler->detail || handler->detail == detail) &&
		   handler->sequential_number < max_sequential_handler_number)
	    {
	      SIGNAL_UNLOCK ();
	      g_closure_invoke (handler->closure,
				return_accu,
				node->n_params + 1,
				instance_and_params,
				&emission.ihint);
	      if (!accumulate (&emission.ihint, emission_return, &accu, accumulator) &&
		  emission.state == EMISSION_RUN)
		emission.state = EMISSION_STOP;
	      SIGNAL_LOCK ();
	      return_value_altered = TRUE;
	      
	      tmp = emission.state == EMISSION_RUN ? handler->next : NULL;
	    }
	  else
	    tmp = handler->next;
	  
	  if (tmp)
	    handler_ref (tmp);
	  handler_unref_R (signal_id, instance, handler_list);
	  handler_list = handler;
	  handler = tmp;
	}
      while (handler);
      
      if (emission.state == EMISSION_STOP)
	goto EMIT_CLEANUP;
      else if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
  emission.ihint.run_type = G_SIGNAL_RUN_LAST;
  
  if ((node->flags & G_SIGNAL_RUN_LAST) && class_closure)
    {
      emission.state = EMISSION_RUN;
      
      emission.chain_type = G_TYPE_FROM_INSTANCE (instance);
      SIGNAL_UNLOCK ();
      g_closure_invoke (class_closure,
			return_accu,
			node->n_params + 1,
			instance_and_params,
			&emission.ihint);
      if (!accumulate (&emission.ihint, emission_return, &accu, accumulator) &&
	  emission.state == EMISSION_RUN)
	emission.state = EMISSION_STOP;
      SIGNAL_LOCK ();
      emission.chain_type = G_TYPE_NONE;
      return_value_altered = TRUE;
      
      if (emission.state == EMISSION_STOP)
	goto EMIT_CLEANUP;
      else if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
  if (handler_list)
    {
      Handler *handler = handler_list;
      
      emission.state = EMISSION_RUN;
      handler_ref (handler);
      do
	{
	  Handler *tmp;
	  
	  if (handler->after && !handler->block_count && (!handler->detail || handler->detail == detail) &&
	      handler->sequential_number < max_sequential_handler_number)
	    {
	      SIGNAL_UNLOCK ();
	      g_closure_invoke (handler->closure,
				return_accu,
				node->n_params + 1,
				instance_and_params,
				&emission.ihint);
	      if (!accumulate (&emission.ihint, emission_return, &accu, accumulator) &&
		  emission.state == EMISSION_RUN)
		emission.state = EMISSION_STOP;
	      SIGNAL_LOCK ();
	      return_value_altered = TRUE;
	      
	      tmp = emission.state == EMISSION_RUN ? handler->next : NULL;
	    }
	  else
	    tmp = handler->next;
	  
	  if (tmp)
	    handler_ref (tmp);
	  handler_unref_R (signal_id, instance, handler);
	  handler = tmp;
	}
      while (handler);
      
      if (emission.state == EMISSION_STOP)
	goto EMIT_CLEANUP;
      else if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
 EMIT_CLEANUP:
  
  emission.ihint.run_type = G_SIGNAL_RUN_CLEANUP;
  
  if ((node->flags & G_SIGNAL_RUN_CLEANUP) && class_closure)
    {
      gboolean need_unset = FALSE;
      
      emission.state = EMISSION_STOP;
      
      emission.chain_type = G_TYPE_FROM_INSTANCE (instance);
      SIGNAL_UNLOCK ();
      if (node->return_type != G_TYPE_NONE && !accumulator)
	{
	  g_value_init (&accu, node->return_type & ~G_SIGNAL_TYPE_STATIC_SCOPE);
	  need_unset = TRUE;
	}
      g_closure_invoke (class_closure,
			node->return_type != G_TYPE_NONE ? &accu : NULL,
			node->n_params + 1,
			instance_and_params,
			&emission.ihint);
      if (need_unset)
	g_value_unset (&accu);
      SIGNAL_LOCK ();
      emission.chain_type = G_TYPE_NONE;
      
      if (emission.state == EMISSION_RESTART)
	goto EMIT_RESTART;
    }
  
  if (handler_list)
    handler_unref_R (signal_id, instance, handler_list);
  
  emission_pop ((node->flags & G_SIGNAL_NO_RECURSE) ? &g_restart_emissions : &g_recursive_emissions, &emission);
  SIGNAL_UNLOCK ();
  if (accumulator)
    g_value_unset (&accu);

  TRACE(GOBJECT_SIGNAL_EMIT_END(node->signal_id, detail, instance, G_TYPE_FROM_INSTANCE (instance)));

  return return_value_altered;
}

static void
add_invalid_closure_notify (Handler  *handler,
			    gpointer  instance)
{
  g_closure_add_invalidate_notifier (handler->closure, instance, invalid_closure_notify);
  handler->has_invalid_closure_notify = 1;
}

static void
remove_invalid_closure_notify (Handler  *handler,
			       gpointer  instance)
{
  if (handler->has_invalid_closure_notify)
    {
      g_closure_remove_invalidate_notifier (handler->closure, instance, invalid_closure_notify);
      handler->has_invalid_closure_notify = 0;
    }
}

static void
invalid_closure_notify (gpointer  instance,
		        GClosure *closure)
{
  Handler *handler;
  guint signal_id;

  SIGNAL_LOCK ();

  handler = handler_lookup (instance, 0, closure, &signal_id);
  g_assert (handler->closure == closure);

  handler->sequential_number = 0;
  handler->block_count = 1;
  handler_unref_R (signal_id, instance, handler);

  SIGNAL_UNLOCK ();
}

static const gchar*
type_debug_name (GType type)
{
  if (type)
    {
      const char *name = g_type_name (type & ~G_SIGNAL_TYPE_STATIC_SCOPE);
      return name ? name : "<unknown>";
    }
  else
    return "<invalid>";
}

/**
 * g_signal_accumulator_true_handled:
 * @ihint: standard #GSignalAccumulator parameter
 * @return_accu: standard #GSignalAccumulator parameter
 * @handler_return: standard #GSignalAccumulator parameter
 * @dummy: standard #GSignalAccumulator parameter
 *
 * A predefined #GSignalAccumulator for signals that return a
 * boolean values. The behavior that this accumulator gives is
 * that a return of %TRUE stops the signal emission: no further
 * callbacks will be invoked, while a return of %FALSE allows
 * the emission to continue. The idea here is that a %TRUE return
 * indicates that the callback handled the signal, and no further
 * handling is needed.
 *
 * Since: 2.4
 *
 * Returns: standard #GSignalAccumulator result
 */
gboolean
g_signal_accumulator_true_handled (GSignalInvocationHint *ihint,
				   GValue                *return_accu,
				   const GValue          *handler_return,
				   gpointer               dummy)
{
  gboolean continue_emission;
  gboolean signal_handled;
  
  signal_handled = g_value_get_boolean (handler_return);
  g_value_set_boolean (return_accu, signal_handled);
  continue_emission = !signal_handled;
  
  return continue_emission;
}

/**
 * g_signal_accumulator_first_wins:
 * @ihint: standard #GSignalAccumulator parameter
 * @return_accu: standard #GSignalAccumulator parameter
 * @handler_return: standard #GSignalAccumulator parameter
 * @dummy: standard #GSignalAccumulator parameter
 *
 * A predefined #GSignalAccumulator for signals intended to be used as a
 * hook for application code to provide a particular value.  Usually
 * only one such value is desired and multiple handlers for the same
 * signal don't make much sense (except for the case of the default
 * handler defined in the class structure, in which case you will
 * usually want the signal connection to override the class handler).
 *
 * This accumulator will use the return value from the first signal
 * handler that is run as the return value for the signal and not run
 * any further handlers (ie: the first handler "wins").
 *
 * Returns: standard #GSignalAccumulator result
 *
 * Since: 2.28
 **/
gboolean
g_signal_accumulator_first_wins (GSignalInvocationHint *ihint,
                                 GValue                *return_accu,
                                 const GValue          *handler_return,
                                 gpointer               dummy)
{
  g_value_copy (handler_return, return_accu);
  return FALSE;
}
