Resources, Concurrency and Local
Reasoning
Peter
O'Hearn, Queen Mary, University of London, UK
In the 1960s Dijkstra suggested that, in order to limit the
complexity of potential process interactions, concurrent programs
should be designed so that different processes behave independently,
except at rare moments of synchronization. In the 1970s, Hoare
and Brinch Hansen argued that debugging and reasoning about concurrent
programs could be considerably simplified using compiler-enforceable
syntactic constraints that preclude interference. Based on such
restrictions Hoare described proof rules for shared-variable
concurrency that were beautifully modular: one could reason locally
about a process, and simple syntactic checks ensured that no other
process could tamper with its state in a way that invalidated the local
reasoning.
The major problem with Hoare and Brinch Hansen's proposal is that its
scope-based approach to resource separation is too restrictive for many
realistic programs. It does not apply to flexible but
unstructured constructs such as semaphores, and the syntactic
checks it relies on are insufficient to rule out interference in the
presence of pointers and aliasing.
There is thus a mismatch, between the intuitive basis of concurrent
programming with resources, where separation remains a vital design
idea, and formal techniques for reasoning about such programs, where
methods based on separation are severely limited. The purpose of
this work is to revisit these issues, using the recent formalism of
separation logic: by using a logic of resources rather than syntactic
constraints, we can overcome the limitations of scope-based approaches,
while retaining their modular character.
We describe a variation on the proof rules of Hoare for conditional
critical regions, using the ``separating conjunction'' connective to
preclude pointer-based interference. With the modified rules we
can at once handle many examples where a linked data structure rather
than, say, an array is used within a process or within a data
abstraction that mediates interprocess interaction.