[Haskell-cafe] STM Finalizers
Roman Cheplyaka
roma at ro-che.info
Thu Jul 30 11:20:25 UTC 2015
Michael,
This looks awesome! Will you try to merge your work into ghc?
I look forward to reading your thesis.
On 30/07/15 14:11, Michael Schröder wrote:
> Hi everyone,
>
> I want to finally announce some work I did as part of my master's thesis
> [1]. It's an extension to GHC's STM implementation. The main idea is to
> introduce a new primitive function
>
> atomicallyWithIO :: STM a -> (a -> IO b) -> IO b
>
> Like the existing atomically operation, atomicallyWithIO performs an STM
> computation. Additionally, it takes a *finalizer*, which is an arbitrary
> I/O action that can depend on the result of the STM computation, and
> combines it with the transaction in such a way that:
>
> 1. The finalizer is only performed if the STM transaction is guaranteed
> to commit.
> 2. The STM transaction only commits if the finalizer finishes without
> raising an exception.
>
>
>
> A motivation of why this is useful:
>
> Say we want to save the results of some STM transaction, i.e. persist
> them to disk. Currently, this is not possible in a transactionally safe
> way. The naive approach would be to first atomically perform some STM
> computation and then independently serialise its result:
>
> do
> x <- atomically m
> serialize x
>
> There are two issues with this. First, another thread could perform a
> second transaction and serialise it before we have finished serialising
> ours, which could result in an inconsistent state between the memory of
> our program and what is stored on disk. Secondly, the function serialize
> might not terminate at all; it could throw an exception or its thread
> could die. Again we would end up with an inconsistent state and possibly
> data loss.
>
> We might try to simply move serialisation into the atomic block, but to
> do this we have to circumvent the types, which should already be a huge
> red flag:
>
> atomically $ do
> x <- m
> unsafeIOToSTM (serialize x)
>
> The problem here is of course that an STM transaction can retry many
> times, which will also result in serialize being executed many times,
> which is probably not something we want. Furthermore, if the thread
> receives an asynchronous exception, the transaction will abort in an
> orderly fashion, while serialize, with its irrevocable side effects,
> cannot be undone.
>
> But with finalizers, the solution is easy:
>
> atomicallyWithIO m serialize
>
>
> I've written a small example application that uses finalizers and other
> stuff from my thesis to build a lightweight STM database framework: [2]
>
> There are more possible uses cases besides serialisation (such as
> interactive transactions) and some interesting issues surrounding
> finalizers (like nesting of transactions) which are discussed in greater
> detail in my thesis [1], which also includes a formal operational
> semantics of the whole thing.
>
> I have implemented finalizers in my fork of GHC [3], if any of you want
> to play around with them yourself. The atomicallyWithIO function is
> exported from the GHC.Conc.Sync module.
>
>
> Cheers,
> Michael
>
>
> [1] https://github.com/mcschroeder/thesis
> [2] https://github.com/mcschroeder/social-example
> [3] https://github.com/mcschroeder/ghc
>
>
>
> _______________________________________________
> Haskell-Cafe mailing list
> Haskell-Cafe at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe
>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 819 bytes
Desc: OpenPGP digital signature
URL: <http://mail.haskell.org/pipermail/haskell-cafe/attachments/20150730/8d575bff/attachment.sig>
More information about the Haskell-Cafe
mailing list