<p dir="ltr">Struct chaperones are the important part, I think.</p>
<p dir="ltr">But the theorem would be false under option 1, I think. Adding contracts can add non-contract errors -- the error you get when a you supply the wrong accessor for struct-chaperone.</p>
<p dir="ltr">Sam</p>
<div class="gmail_quote">On Jul 24, 2014 7:54 PM, "Robby Findler" <<a href="mailto:robby@eecs.northwestern.edu">robby@eecs.northwestern.edu</a>> wrote:<br type="attribution"><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
Ah, nope. That model doesn't include function chaperones!<br>
<br>
Robby<br>
<br>
On Thu, Jul 24, 2014 at 6:14 PM, Robby Findler<br>
<<a href="mailto:robby@eecs.northwestern.edu">robby@eecs.northwestern.edu</a>> wrote:<br>
> I also lean towards #2. What does the redex model say? Most of those<br>
> pieces are in it, I think.<br>
><br>
> Robby<br>
><br>
> On Thu, Jul 24, 2014 at 3:25 PM, Matthew Flatt <<a href="mailto:mflatt@cs.utah.edu">mflatt@cs.utah.edu</a>> wrote:<br>
>> Nice example. Offhand, I think that #2 is right, but I'll have to look<br>
>> at it more to be sure.<br>
>><br>
>> At Thu, 24 Jul 2014 15:45:18 -0400, Sam Tobin-Hochstadt wrote:<br>
>>> Consider the following module:<br>
>>><br>
>>> (module m racket<br>
>>>   (struct x [a])<br>
>>>   (define v1 (x 'secret))<br>
>>>   (define v2 (x 'public))<br>
>>>   (provide v1 v2)<br>
>>>   (provide/contract [x-a (-> x? (not/c 'secret))]))<br>
>>><br>
>>> It appears that this ensures that you can't get 'secret. But, it turns<br>
>>> out that I can write a function outside of `m` that behaves like `x-a`<br>
>>> without the contract:<br>
>>><br>
>>> (require (prefix-in m: 'm))<br>
>>><br>
>>> (define (x-a v)<br>
>>>   (define out #f)<br>
>>>   (with-handlers ([void void])<br>
>>>     (m:x-a (chaperone-struct v m:x-a (λ (s v) (set! out v) v))))<br>
>>>   out)<br>
>>><br>
>>> Now this works:<br>
>>><br>
>>> (displayln (x-a m:v1)) ;; => 'secret<br>
>>><br>
>>> The problem is that `m:x-a` is treated as a<br>
>>> `struct-accessor-procedure?`, which is a capability for accessing the<br>
>>> a field, even though it's a significantly restricted capability.<br>
>>><br>
>>> There are a couple possible solutions I've thought of:<br>
>>><br>
>>> 1. Require a non-chaperoned/impersonated accessor.<br>
>>> 2. Actually use the chaperoned/impersonatored accessor to get the<br>
>>> value out instead of the underlying accessor.<br>
>>><br>
>>> 1 is a little less expressive. But note that 2 means that you have to<br>
>>> only allow chaperoned procedures with `chaperone-struct`, and imposes<br>
>>> significant complication on the runtime.<br>
>>><br>
>>> I favor 1.<br>
>>><br>
>>> Sam<br>
>>><br>
>>> _________________________<br>
>>>   Racket Developers list:<br>
>>>   <a href="http://lists.racket-lang.org/dev" target="_blank">http://lists.racket-lang.org/dev</a><br>
>><br>
>> _________________________<br>
>>   Racket Developers list:<br>
>>   <a href="http://lists.racket-lang.org/dev" target="_blank">http://lists.racket-lang.org/dev</a><br>
</blockquote></div>