diff --git a/Data/GI/Base/BasicConversions.hsc b/Data/GI/Base/BasicConversions.hsc
--- a/Data/GI/Base/BasicConversions.hsc
+++ b/Data/GI/Base/BasicConversions.hsc
@@ -89,7 +89,6 @@
 
 import Data.GI.Base.BasicTypes
 import Data.GI.Base.CallStack (HasCallStack)
-import Data.GI.Base.GHashTable (GEqualFunc, GHashFunc)
 import Data.GI.Base.ManagedPtr (copyBoxedPtr)
 import Data.GI.Base.Utils (allocBytes, callocBytes, memcpy, freeMem,
                            checkUnexpectedReturnNULL)
diff --git a/Data/GI/Base/BasicTypes.hsc b/Data/GI/Base/BasicTypes.hsc
--- a/Data/GI/Base/BasicTypes.hsc
+++ b/Data/GI/Base/BasicTypes.hsc
@@ -39,6 +39,9 @@
 
     , PtrWrapped(..)
     , GDestroyNotify
+
+    , GHashFunc
+    , GEqualFunc
     ) where
 
 import Control.Exception (Exception)
@@ -47,14 +50,15 @@
 import Data.IORef (IORef)
 import qualified Data.Text as T
 import Data.Typeable (Typeable)
+import Data.Int
 import Data.Word
 
 import Foreign.C (CString, peekCString)
 import Foreign.Ptr (Ptr, FunPtr)
 import Foreign.ForeignPtr (ForeignPtr)
 
-import Data.GI.Base.CallStack (CallStack)
 import {-# SOURCE #-} Data.GI.Base.Overloading (HasParentTypes)
+import Data.GI.Base.CallStack (CallStack)
 
 #include <glib-object.h>
 
@@ -201,8 +205,8 @@
 -- wrapped into a pointer. We encode such a type as follows.
 newtype PtrWrapped a = PtrWrapped {unwrapPtr :: Ptr a}
 
--- | Destroy the memory associated with a given pointer.
-type GDestroyNotify a = FunPtr (Ptr a -> IO ())
+-- | Destroy the memory pointed to by a given pointer type.
+type GDestroyNotify ptr = FunPtr (ptr -> IO ())
 
 -- | Free the given 'GList'.
 foreign import ccall "g_list_free" g_list_free ::
@@ -211,3 +215,9 @@
 -- | Free the given 'GSList'.
 foreign import ccall "g_slist_free" g_slist_free ::
     Ptr (GSList a) -> IO ()
+
+-- | A pointer to a hashing function on the C side.
+type GHashFunc a = FunPtr (PtrWrapped a -> IO #{type guint})
+
+-- | A pointer to an equality checking function on the C side.
+type GEqualFunc a = FunPtr (PtrWrapped a -> PtrWrapped a -> IO #{type gboolean})
diff --git a/Data/GI/Base/GHashTable.hsc b/Data/GI/Base/GHashTable.hsc
--- a/Data/GI/Base/GHashTable.hsc
+++ b/Data/GI/Base/GHashTable.hsc
@@ -21,24 +21,18 @@
     , gStrEqual
     , cstringPackPtr
     , cstringUnpackPtr
+    , gvaluePackPtr
+    , gvalueUnpackPtr
     ) where
 
-import Data.Int
-import Data.Word
-
 import Foreign.C
-import Foreign.Ptr (Ptr, castPtr, FunPtr)
+import Foreign.Ptr (Ptr, castPtr)
 
-import Data.GI.Base.BasicTypes (PtrWrapped(..))
+import Data.GI.Base.BasicTypes (PtrWrapped(..), GHashFunc, GEqualFunc)
+import Data.GI.Base.GValue (GValue)
 
 #include <glib-object.h>
 
--- | A pointer to a hashing function on the C side.
-type GHashFunc a = FunPtr (PtrWrapped a -> IO #{type guint})
-
--- | A pointer to an equality checking function on the C side.
-type GEqualFunc a = FunPtr (PtrWrapped a -> PtrWrapped a -> IO #{type gboolean})
-
 -- | Compute the hash for a `Ptr`.
 foreign import ccall "&g_direct_hash" gDirectHash :: GHashFunc (Ptr a)
 
@@ -66,3 +60,12 @@
 -- | Extract a `CString` wrapped into a `Ptr` coming from a `GHashTable`.
 cstringUnpackPtr :: PtrWrapped CString -> CString
 cstringUnpackPtr = ptrUnpackPtr
+
+-- | Pack a `Ptr` to `GValue` into a `Ptr` than can go into a `GHashTable`.
+gvaluePackPtr :: Ptr GValue -> PtrWrapped (Ptr GValue)
+gvaluePackPtr = ptrPackPtr
+
+-- | Extract a `Ptr` to `GValue` wrapped into a `Ptr` coming from a
+-- `GHashTable`.
+gvalueUnpackPtr :: PtrWrapped (Ptr GValue) -> Ptr GValue
+gvalueUnpackPtr = ptrUnpackPtr
diff --git a/Data/GI/Base/GObject.hsc b/Data/GI/Base/GObject.hsc
--- a/Data/GI/Base/GObject.hsc
+++ b/Data/GI/Base/GObject.hsc
@@ -333,10 +333,10 @@
     else return Nothing
 
 foreign import ccall "&hs_free_stable_ptr" ptr_to_hs_free_stable_ptr ::
-        FunPtr (GDestroyNotify a)
+        GDestroyNotify (Ptr ())
 
 foreign import ccall g_object_set_qdata_full ::
-        Ptr a -> GQuark b -> Ptr () -> FunPtr (GDestroyNotify ()) -> IO ()
+        Ptr a -> GQuark b -> Ptr () -> GDestroyNotify (Ptr ()) -> IO ()
 
 -- | Set the value of the user data for the given `GObject` to a
 -- `StablePtr` to the given Haskell object. The `StablePtr` will be
diff --git a/Data/GI/Base/GValue.hs b/Data/GI/Base/GValue.hs
--- a/Data/GI/Base/GValue.hs
+++ b/Data/GI/Base/GValue.hs
@@ -13,6 +13,7 @@
     , toGValue
     , fromGValue
     , GValueConstruct(..)
+    , ptr_to_gvalue_free
 
     , newGValue
     , buildGValue
@@ -55,32 +56,32 @@
 import Foreign.C.Types (CInt(..), CUInt(..), CFloat(..), CDouble(..),
                         CLong(..), CULong(..))
 import Foreign.C.String (CString)
-import Foreign.Ptr (Ptr, nullPtr, plusPtr)
+import Foreign.Ptr (Ptr, nullPtr, plusPtr, FunPtr)
 import Foreign.StablePtr (StablePtr, castStablePtrToPtr, castPtrToStablePtr)
 
 import Data.GI.Base.BasicTypes
 import Data.GI.Base.BasicConversions (cstringToText, textToCString)
 import Data.GI.Base.GType
 import Data.GI.Base.ManagedPtr
-import Data.GI.Base.Overloading (HasParentTypes, ParentTypes)
 import Data.GI.Base.Utils (callocBytes, freeMem)
 import Data.GI.Base.Internal.CTypes (cgvalueSize)
+import Data.GI.Base.Overloading (ParentTypes, HasParentTypes)
 
 -- | Haskell-side representation of a @GValue@.
 newtype GValue = GValue (ManagedPtr GValue)
 
--- | A convenience alias for @`Nothing` :: `Maybe` `GValue`@.
-noGValue :: Maybe GValue
-noGValue = Nothing
-
-foreign import ccall unsafe "g_value_get_type" c_g_value_get_type ::
-    IO GType
+-- | A pointer to a function freeing GValues.
+foreign import ccall "&haskell_gi_gvalue_free" ptr_to_gvalue_free ::
+    FunPtr (Ptr GValue -> IO ())
 
 -- | There are no types in the bindings that a `GValue` can be safely
 -- cast to.
 type instance ParentTypes GValue = '[]
 instance HasParentTypes GValue
 
+foreign import ccall unsafe "g_value_get_type" c_g_value_get_type ::
+    IO GType
+
 -- | Find the associated `GType` for `GValue`.
 instance TypedObject GValue where
   glibType = c_g_value_get_type
@@ -139,6 +140,10 @@
 -- | Unset the `GValue`, freeing all resources associated to it.
 unsetGValue :: Ptr GValue -> IO ()
 unsetGValue = g_value_unset
+
+-- | A convenient alias for @Nothing :: Maybe GValue@.
+noGValue :: Maybe GValue
+noGValue = Nothing
 
 -- | Class for types that can be marshaled back and forth between
 -- Haskell values and `GValue`s. These are low-level methods, you
diff --git a/Data/GI/Base/Overloading.hs b/Data/GI/Base/Overloading.hs
--- a/Data/GI/Base/Overloading.hs
+++ b/Data/GI/Base/Overloading.hs
@@ -58,6 +58,22 @@
     FindElement m ('(m, o) ': ms) typeError = o
     FindElement m ('(m', o) ': ms) typeError = FindElement m ms typeError
 
+-- | All the types that are ascendants of this type, including
+-- interfaces that the type implements.
+type family ParentTypes a :: [Type]
+
+-- | A constraint on a type, to be fulfilled whenever it has a type
+-- instance for `ParentTypes`. This leads to nicer errors, thanks to
+-- the overlappable instance below.
+class HasParentTypes (o :: Type)
+
+-- | Default instance, which will give rise to an error for types
+-- without an associated `ParentTypes` instance.
+instance {-# OVERLAPPABLE #-}
+    TypeError ('Text "Type ‘" ':<>: 'ShowType a ':<>:
+               'Text "’ does not have any known parent types.")
+    => HasParentTypes a
+
 -- | Check whether a type appears in a list. We specialize the
 -- names/types a bit so the error messages are more informative.
 type family CheckForAncestorType t (a :: Type) (as :: [Type]) :: Constraint where
@@ -74,22 +90,6 @@
     -- Every object is defined to be a descendant of itself.
     IsDescendantOf d d = ()
     IsDescendantOf p d = CheckForAncestorType d p (ParentTypes d)
-
--- | All the types that are ascendants of this type, including
--- interfaces that the type implements.
-type family ParentTypes a :: [Type]
-
--- | A constraint on a type, to be fulfilled whenever it has a type
--- instance for `ParentTypes`. This leads to nicer errors, thanks to
--- the overlappable instance below.
-class HasParentTypes (o :: Type)
-
--- | Default instance, which will give rise to an error for types
--- without an associated `ParentTypes` instance.
-instance {-# OVERLAPPABLE #-}
-    TypeError ('Text "Type ‘" ':<>: 'ShowType a ':<>:
-               'Text "’ does not have any known parent types.")
-    => HasParentTypes a
 
 -- | Safe coercions to a parent class. For instance:
 --
diff --git a/Data/GI/Base/Overloading.hs-boot b/Data/GI/Base/Overloading.hs-boot
--- a/Data/GI/Base/Overloading.hs-boot
+++ b/Data/GI/Base/Overloading.hs-boot
@@ -1,3 +1,3 @@
 module Data.GI.Base.Overloading (HasParentTypes) where
 
-class HasParentTypes o
+class HasParentTypes a
diff --git a/csrc/hsgclosure.c b/csrc/hsgclosure.c
--- a/csrc/hsgclosure.c
+++ b/csrc/hsgclosure.c
@@ -202,6 +202,18 @@
   g_idle_add(g_object_unref_in_main_loop, obj);
 }
 
+static gboolean gvalue_unref_in_main_loop(void *gv)
+{
+  g_boxed_free(G_TYPE_VALUE, gv);
+
+  return FALSE; /* Do not invoke again */
+}
+
+void haskell_gi_gvalue_free(GValue *gv)
+{
+  g_idle_add(gvalue_unref_in_main_loop, gv);
+}
+
 /**
  * dbg_g_object_new:
  * @gtype: #GType for the object to construct.
diff --git a/haskell-gi-base.cabal b/haskell-gi-base.cabal
--- a/haskell-gi-base.cabal
+++ b/haskell-gi-base.cabal
@@ -1,5 +1,5 @@
 name:                haskell-gi-base
-version:             0.26.0
+version:             0.26.1
 synopsis:            Foundation for libraries generated by haskell-gi
 description:         Foundation for libraries generated by haskell-gi
 homepage:            https://github.com/haskell-gi/haskell-gi
