On this page:
place
place-wait
place?
place-channel
place-channel-send
place-channel-recv
place-channel?
place-channel-send/ recv
10.5.1 Basic Example
10.5.2 Place Channels
10.5.3 Message Passing Parallelism
10.5.4 Architecture and Garbage Collection

10.5 Places: Coarse-grained Parallelism

Places enable the development of parallel programs that take advantage of machines with multiple processors, cores, or hardware threads.

The bindings documented in this section are provided by the racket/place and racket libraries, but not racket/base.

Note: currently, parallel support for place is disabled by default, and using it will raise an exception. Support can only be enabled if you build Racket yourself, and pass --enable-places to configure. This works only for racket (not gracket), and it is supported only on Linux x86/x86_64, and Mac OS X x86/x86_64 platforms.

(place module-path start-proc)  place?
  module-path : module-path?
  start-proc : symbol?
Starts running start-proc in parallel. start-proc must be a function defined in module-path. The place procedure returns immediately with a place descriptor value representing the newly constructed place. Each place descriptor value is also a place-channel that permits communication with the place.

(place-wait p)  exact-integer?
  p : place?
Returns the return value of a completed place p, blocking until the place completes (if it has not already completed).

(place? x)  boolean?
  x : any/c
Returns #t if x is a place-descriptor value, #f otherwise.

Returns two place-channel endpoint objects.

One place-channel endpoint should be used by the current place to send messages to a destination place.

The other place-channel endpoint should be sent to a destination place over an existing place-channel.

(place-channel-send ch x)  void
  ch : place-channel?
  x : any/c
Sends an immutable message x on channel ch.

Returns an immutable message received on channel ch.

(place-channel? x)  boolean?
  x : any/c
Returns #t if x is a place-channel object.

(place-channel-send/recv ch x)  void
  ch : place-channel?
  x : any/c
Sends an immutable message x on channel ch and then waits for a repy message. Returns an immutable message received on channel ch.

10.5.1 Basic Example

This code launches two places, echos a message to them and then waits for the places to complete and return.

  (let ([pls (for/list ([i (in-range 2)])
                (place "place-worker.rkt" 'place-main))])
     (for ([i (in-range 2)]
           [p pls])
        (place-channel-send p i)
        (printf "~a\n" (place-channel-recv p)))
     (map place-wait pls))

This is the code for the place-worker.ss module that each place will execute.

  (module place-worker racket
    (provide place-main)
  
    (define (place-main ch)
      (place-channel-send ch (format "Hello from place ~a" (place-channel-recv ch)))))

10.5.2 Place Channels

Place channels can be used with place-channel-recv, or as a synchronizable event (see Events) to receive a value through the channel. The channel can be used with place-channel-send to send a value through the channel.

10.5.3 Message Passing Parallelism

Places communicate by passing messages on place-channels. Only atomic values, immutable pairs, vectors, and structs can be communicated across places channels.

10.5.4 Architecture and Garbage Collection

Places enables a shared memory space between all places. References from the shared memory space back into a places memory space. The invariant of allowing no backpointers is enforced by only allowing immutable datastructures to be deep copied into the shared memory space.

However, mutation of atomic values in the shared memory space is permitted to improve performace of shared-memory parallel programs.

Special functions such as shared-flvector and shared-bytes allocate vectors of mutable atomic values into the shared memory space.

Parallel mutation of these atomic values can possibly lead to data races, but will not cause racket to crash. In practice however, parallel tasks usually write to disjoint partitions of a shared vector.

Places are allowed to garbage collect independently of one another. The shared-memory collector, however, has to pause all places before it can collect garbage.