diff --git a/adjunctions.cabal b/adjunctions.cabal
--- a/adjunctions.cabal
+++ b/adjunctions.cabal
@@ -1,6 +1,6 @@
 name:          adjunctions
 category:      Data Structures, Adjunctions
-version:       3.0.1
+version:       3.1
 license:       BSD3
 cabal-version: >= 1.6
 license-file:  LICENSE
@@ -36,14 +36,15 @@
     transformers           >= 0.2     && < 0.4,
     mtl                    >= 2.0.1   && < 2.2,
     containers             >= 0.3     && < 0.6,
-    comonad                >= 3,
-    contravariant          >= 0.2.0.1,
-    distributive           >= 0.2.2,
-    semigroupoids          >= 3,
-    void                   >= 0.5.5.1,
-    keys                   >= 3,
-    comonad-transformers   >= 3,
-    representable-functors >= 3.0.0.1
+    comonad                >= 3       && < 4,
+    contravariant          >= 0.2.0.1 && < 1,
+    distributive           >= 0.2.2   && < 1,
+    semigroupoids          >= 3       && < 4,
+    void                   >= 0.5.5.1 && < 1,
+    keys                   >= 3       && < 4,
+    comonad-transformers   >= 3       && < 4,
+    representable-functors >= 3.0.0.1 && < 4,
+    free                   >= 3       && < 4
 
   exposed-modules:
     Data.Functor.Adjunction
diff --git a/src/Data/Functor/Adjunction.hs b/src/Data/Functor/Adjunction.hs
--- a/src/Data/Functor/Adjunction.hs
+++ b/src/Data/Functor/Adjunction.hs
@@ -18,6 +18,7 @@
   ( Adjunction(..)
   , tabulateAdjunction
   , indexAdjunction
+  , zapWithAdjunction
   , zipR, unzipR
   , unabsurdL, absurdL
   , cozipL, uncozipL
@@ -27,15 +28,20 @@
 
 import Control.Applicative
 import Control.Arrow ((&&&), (|||))
+import Control.Monad.Free
 import Control.Monad.Instances ()
 import Control.Monad.Trans.Identity
 import Control.Monad.Trans.Reader
 import Control.Monad.Trans.Writer
+import Control.Comonad
+import Control.Comonad.Cofree
 import Control.Comonad.Trans.Env
 import Control.Comonad.Trans.Traced
 
 import Data.Functor.Identity
+import Data.Functor.Coproduct
 import Data.Functor.Compose
+import Data.Functor.Product
 import Data.Functor.Representable
 import Data.Void
 
@@ -83,6 +89,9 @@
 indexAdjunction :: Adjunction f u => u b -> f a -> b
 indexAdjunction = rightAdjunct . const
 
+zapWithAdjunction :: Adjunction f u => (a -> b -> c) -> u a -> f b -> c
+zapWithAdjunction f ua = rightAdjunct (\b -> fmap (flip f b) ua)
+
 splitL :: Adjunction f u => f a -> (a, f ())
 splitL = rightAdjunct (flip leftAdjunct () . (,))
 
@@ -150,3 +159,17 @@
          Adjunction (Compose f' f) (Compose g g') where
   unit   = Compose . leftAdjunct (leftAdjunct Compose) 
   counit = rightAdjunct (rightAdjunct getCompose) . getCompose
+
+instance (Adjunction f g, Adjunction f' g') => 
+         Adjunction (Coproduct f f') (Product g g') where
+  unit a = Pair (leftAdjunct left a) (leftAdjunct right a)
+  counit = coproduct (rightAdjunct fstP) (rightAdjunct sndP)
+    where
+      fstP (Pair x _) = x
+      sndP (Pair _ x) = x
+
+instance Adjunction f u => 
+         Adjunction (Free f) (Cofree u) where
+  unit a = return a :< tabulateAdjunction (\k -> leftAdjunct (wrap . flip unsplitL k) a)
+  counit (Pure a) = extract a
+  counit (Free k) = rightAdjunct (flip indexAdjunction k . unwrap) (extractL k)
