diff --git a/PEOPLE b/PEOPLE
--- a/PEOPLE
+++ b/PEOPLE
@@ -3,3 +3,4 @@
 discussions about the library design.
 
 Renzo Carbonara
+Gabriel Gonzalez
diff --git a/examples/chat-tcp.hs b/examples/chat-tcp.hs
--- a/examples/chat-tcp.hs
+++ b/examples/chat-tcp.hs
@@ -16,13 +16,13 @@
 import           Data.Monoid                  ((<>))
 import qualified Data.Text                    as T
 import           Data.Text.Encoding           (decodeUtf8, encodeUtf8)
-import           Network.Simple.TCP           (listen, acceptFork)
+import           Network.Simple.TCP           (listen, acceptFork, withSocketsDo)
 import           Network.Socket               (Socket, SockAddr)
 import           Network.Socket.ByteString    (recv, sendAll)
 
 
 main :: IO ()
-main = do
+main = withSocketsDo $ do
    bchan <- newTChanIO :: IO (TChan T.Text)
             -- ^XXX we should really use 'newBroadcastTCHanIO' from STM-2.4
    listen "*" "9000" $ \(lsock, laddr) -> do
diff --git a/examples/echo-tcp.hs b/examples/echo-tcp.hs
--- a/examples/echo-tcp.hs
+++ b/examples/echo-tcp.hs
@@ -14,7 +14,7 @@
 
 
 main :: IO ()
-main = do
+main = T.withSocketsDo $ do
     T.listen "*" "9000" $ \(lsock, laddr) -> do
       putStrLn $ "Listening for TCP connections at " ++ show laddr
       forever . T.acceptFork lsock $ \(csock, caddr) -> do
diff --git a/network-simple.cabal b/network-simple.cabal
--- a/network-simple.cabal
+++ b/network-simple.cabal
@@ -1,5 +1,5 @@
 name:                network-simple
-version:             0.2.0.1
+version:             0.2.1.0
 homepage:            https://github.com/k0001/network-simple
 bug-reports:         https://github.com/k0001/network-simple/issues
 license:             BSD3
@@ -33,29 +33,4 @@
   other-modules:     Network.Simple.Internal
   build-depends:     base (>=4.5 && < 5)
                    , network (>=2.3 && <2.5)
-
-
-
-
-------------------------------------------------------------------------
--- Examples. All built when the 'examples' flag is given.
-
-flag examples
-  description:         Build examples
-  default:             False
-
-executable network-simple-example-echo-tcp
-  if !flag(examples)
-    buildable: False
-  hs-source-dirs:      examples
-  main-is:             echo-tcp.hs
-  build-depends:       base, bytestring, network-simple, network
-
-executable network-simple-example-chat-tcp
-  if !flag(examples)
-    buildable: False
-  hs-source-dirs:      examples
-  main-is:             chat-tcp.hs
-  build-depends:       base, bytestring, network-simple, network, text,
-                       stm
-
+                   , bytestring (>=0.9.2.1 && <0.11)
diff --git a/src/Network/Simple/TCP.hs b/src/Network/Simple/TCP.hs
--- a/src/Network/Simple/TCP.hs
+++ b/src/Network/Simple/TCP.hs
@@ -26,20 +26,30 @@
   , accept
   , acceptFork
 
+  -- * Utils
+  , recv
+  , send
+
   -- * Low level support
   , bindSock
   , connectSock
 
-  -- * Exports
+  -- * Note to Windows users
+  -- $windows-users
+  , NS.withSocketsDo
+
+  -- * Types
   , HostPreference(..)
   ) where
 
 import           Control.Concurrent             (ThreadId, forkIO)
 import qualified Control.Exception              as E
 import           Control.Monad
+import qualified Data.ByteString                as BS
 import           Data.List                      (partition)
 import qualified Network.Socket                 as NS
 import           Network.Simple.Internal
+import qualified Network.Socket.ByteString
 
 --------------------------------------------------------------------------------
 -- $tcp-101
@@ -74,13 +84,44 @@
 
 --------------------------------------------------------------------------------
 
+-- $windows-users
+--
+-- If you are running Windows, then you /must/ call 'NS.withSocketsDo', just
+-- once, right at the beginning of your program. That is, change your program's
+-- 'main' function from:
+--
+-- @
+-- main = do
+--   print \"Hello world\"
+--   -- rest of the program...
+-- @
+--
+-- To:
+--
+-- @
+-- main = 'NS.withSocketsDo' $ do
+--   print \"Hello world\"
+--   -- rest of the program...
+-- @
+--
+-- If you don't do this, your networking code won't work and you will get many
+-- unexpected errors at runtime. If you use an operating system other than
+-- Windows then you don't need to do this, but it is harmless to do it, so it's
+-- recommended that you do for portability reasons.
+
+--------------------------------------------------------------------------------
+
+
 -- $client-side
 --
 -- Here's how you could run a TCP client:
 --
--- > connect "www.example.org" "80" $ \(connectionSocket, remoteAddr) -> do
--- >   putStrLn $ "Connection established to " ++ show remoteAddr
--- >   -- now you may use connectionSocket as you please within this scope.
+-- @
+-- 'connect' \"www.example.org\" \"80\" $ \(connectionSocket, remoteAddr) -> do
+--   putStrLn $ \"Connection established to \" ++ show remoteAddr
+--   -- Now you may use connectionSocket as you please within this scope,
+--   -- possibly using 'recv' and 'send' to interact with the remote end.
+-- @
 
 -- | Connect to a TCP server and use the connection.
 --
@@ -104,9 +145,12 @@
 -- Here's how you can run a TCP server that handles in different threads each
 -- incoming connection to port @8000@ at IPv4 address @127.0.0.1@:
 --
--- > serve (Host "127.0.0.1") "8000" $ \(connectionSocket, remoteAddr) -> do
--- >   putStrLn $ "TCP connection established from " ++ show remoteAddr
--- >   -- now you may use connectionSocket as you please within this scope.
+-- @
+-- 'serve' ('Host' \"127.0.0.1\") \"8000\" $ \(connectionSocket, remoteAddr) -> do
+--   putStrLn $ \"TCP connection established from \" ++ show remoteAddr
+--   -- Now you may use connectionSocket as you please within this scope,
+--   -- possibly using 'recv' and 'send' to interact with the remote end.
+-- @
 --
 -- If you need more control on the way your server runs, then you can use more
 -- advanced functions such as 'listen', 'accept' and 'acceptFork'.
@@ -247,6 +291,26 @@
       NS.setSocketOption sock NS.ReuseAddr 1
       NS.bindSocket sock sockAddr
       return (sock, sockAddr)
+
+--------------------------------------------------------------------------------
+-- Utils
+
+-- | Read up to a limited number of bytes from a socket.
+--
+-- Returns `Nothing` if the remote end closed the connection or end-of-input was
+-- reached. The number of returned bytes might be less than the specified limit.
+recv :: NS.Socket -> Int -> IO (Maybe BS.ByteString)
+recv sock nbytes = do
+     bs <- Network.Socket.ByteString.recv sock nbytes
+     if BS.null bs
+        then return Nothing
+        else return (Just bs)
+{-# INLINE recv #-}
+
+-- | Writes the given bytes to the socket.
+send :: NS.Socket -> BS.ByteString -> IO ()
+send = Network.Socket.ByteString.sendAll
+{-# INLINE send #-}
 
 --------------------------------------------------------------------------------
 
