diff --git a/crdt.cabal b/crdt.cabal
--- a/crdt.cabal
+++ b/crdt.cabal
@@ -1,5 +1,5 @@
 name: crdt
-version: 10.2
+version: 10.3
           -- ^ ComVer
 category: Distributed Systems
 copyright:
diff --git a/lib/CRDT/Cm/RGA.hs b/lib/CRDT/Cm/RGA.hs
--- a/lib/CRDT/Cm/RGA.hs
+++ b/lib/CRDT/Cm/RGA.hs
@@ -84,8 +84,7 @@
             case Map.lookupMax vertexIxs of
                 Just (LamportTime maxKnownTime _, _) -> advance maxKnownTime
                 Nothing                              -> pure ()
-            newId <- getTime
-            pure $ OpAddAfter mOldId atom newId
+            OpAddAfter mOldId atom <$> getTime
 
     makeOp (Remove w) payload
         | lookup w payload = Just . pure $ OpRemove w
diff --git a/lib/CRDT/LamportClock.hs b/lib/CRDT/LamportClock.hs
--- a/lib/CRDT/LamportClock.hs
+++ b/lib/CRDT/LamportClock.hs
@@ -84,8 +84,10 @@
         timeVar <- ask
         lift $ atomically $ modifyTVar' timeVar $ max time
 
-    getTimes n' = do
-        timeRangeStart <- LamportClock $ do
+    getTimes n' = LamportTime <$> getTimes' <*> getPid
+      where
+        n = max n' 1
+        getTimes' = LamportClock $ do
             timeVar <- ask
             lift $ do
                 realTime <- getRealLocalTime
@@ -94,10 +96,6 @@
                     let timeRangeStart = max realTime (timeCur + 1)
                     writeTVar timeVar $ timeRangeStart + n - 1
                     pure timeRangeStart
-        pid <- getPid
-        pure $ LamportTime timeRangeStart pid
-      where
-        n = max n' 1
 
 instance Process m => Process (ReaderT r m) where
     getPid = lift getPid
diff --git a/lib/CRDT/LamportClock/Simulation.hs b/lib/CRDT/LamportClock/Simulation.hs
--- a/lib/CRDT/LamportClock/Simulation.hs
+++ b/lib/CRDT/LamportClock/Simulation.hs
@@ -22,6 +22,7 @@
                                        throwError)
 import           Control.Monad.Fail (MonadFail)
 import qualified Control.Monad.Fail as Fail
+import           Control.Monad.IO.Class (MonadIO, liftIO)
 import           Control.Monad.Reader (ReaderT, ask, runReaderT)
 import           Control.Monad.State.Strict (StateT, evalState, evalStateT,
                                              modify, state)
@@ -53,6 +54,9 @@
 instance Monad m => MonadFail (LamportClockSimT m) where
     fail = throwError
 
+instance MonadIO m => MonadIO (LamportClockSimT m) where
+    liftIO io = LamportClockSim $ liftIO io
+
 type LamportClockSim = LamportClockSimT Identity
 
 -- | ProcessSim inside Lamport clock simulation.
@@ -82,6 +86,9 @@
         advancePS = \case
             Nothing      -> time
             Just current -> max time current
+
+instance MonadIO m => MonadIO (ProcessSimT m) where
+    liftIO io = ProcessSim $ liftIO io
 
 runLamportClockSim :: LamportClockSim a -> Either String a
 runLamportClockSim (LamportClockSim action) =
diff --git a/lib/Data/Semilattice.hs b/lib/Data/Semilattice.hs
--- a/lib/Data/Semilattice.hs
+++ b/lib/Data/Semilattice.hs
@@ -36,3 +36,5 @@
 instance Ord a => Semilattice (Max a)
 
 instance Ord a => Semilattice (Set a)
+
+instance Semilattice a => Semilattice (Maybe a)
