
I have a question on places, but most likely it is also related to rackunit and interaction with test
submodules. Take a look: #lang racket/base
(module+ test
(require rackunit racket/place)
(define v 2)
(check-= (place-channel-get (place/context ch (place-channel-put v)))
v))
This goes into an infinite loop. I understand that one needs to be careful when putting calls to place in the top-level and why an infinite loop occurs there. However, I can’t seem to figure out why it would occur here. I run it with raco test place-test.rkt
and places create places, which in turn create more places. I was expecting raco test
in this case to call the test submodule, which does create a the first place, but there’s no reason for the place then to create yet another place since itself should not be executing the test
submodule automatically. But somehow, it is. Why is this happening?

@pocmatos I believe that the restriction is that the dynamic evaluation of the place
expression must not happen during the initialization of the module (or submodule) where the place
expression statically occurs, and your code is doing that. The reason (IIRC) is that place
lifts its body as a definition to the top level of the enclosing module and sends the module name and defined name to the new place to execute. The new place fetches the code to run by doing dynamic-require
, which initializes the module where the place
expression occurred, and if initializing that module means evaluating the place
expression again, you get the loop.

What you say makes sense but it only fits my view of things until you say: where the place expression *statically* occurs

Still confuses me, why the dynamic-require
would initialize the module where the place
expression occurred. I thought it would only initialize the top-level.

In the newly created place, the module containing the place/context
expression has to be instantiated. In this case, that’s the test
submodule. Instantiating the test
submodule runs the body of the submodule, which includes a check-=
form that has a place/context
subexpression, and evaluating that subexpression creates a new place that instantiates the test
submodule…

ah of course. I forgot that in the new place, we need to instantiate the place/context
in order to get the place-body-n
module to call in the place.

Although this is not a serious issue, it’s quite annoying to have to worry about this. I understand that this is due to the way places are implemented but is there an alternative implementation in which one could minimize or remove this problem?

We never found a different design. FWIW, I usually put the place/context
call in a function in the enclosing module, and then call the function from a submodule like main
and test
.

Thanks. Yes, I do that in practice too. However, I was trying to see the best way to run tests involving place calls. I just noticed from the racket place tests, that test submodules are not used. Instead tests are ran as programs. Makes sense in this case. Thanks.

@heymatthewoden has joined the channel

@pocmatos maybe there could be a protocol where place
or place/context
sends an initial message to conditionally avoid running itself?

place/context
might be better since it already sends an initial message

Maybe under a new name place/safe
? That could be something interesting to try.

Might be a bad name, giving the impression the other place is unsafe… in any case the idea is interesting.

@smartmakerfest has joined the channel

Can someone block smartmakerfest?

done