[racket-dev] When is it safe to not rename a runtime value in a macro?

From: Neil Toronto (neil.toronto at gmail.com)
Date: Sat Aug 25 12:19:30 EDT 2012

A lot of macros start by renaming some syntax that's assumed to 
eventually represent a runtime value, like the `or' macro does:

 > (syntax->datum (expand-syntax #'(or #t #f)))
'(let-values (((or-part) '#t)) (if or-part or-part '#f))

But it's not always a good thing, particularly when the output will be 
processed by another macro, and parts will be tested using an 
`identifier=?' function. For example, my `inline-sort' takes `<' as an 
argument. So

   (inline-sort < a b)

expands to

   (let ([lt? <] [temp1 a] [temp2 b])
     (if (lt? temp1 temp2) (values temp1 temp2) (values temp2 temp1)))

Well, it did at first. When I discovered that Typed Racket's optimizer 
would never detect that `lt?' is actually `<' and replace it with 
`unsafe-fl<', I altered the macro to detect when the `<' is an 
identifier, and not rename it with a `let'.

I know that I should assert my rights under the Macro Bill. But I like 
to program defensively. So what's safe to not rename? I think the 
following are:

symbol
number
string
bytes
null
character
regexp
prefab struct key

Also, should I ever have to intern syntax that's one of these kinds of 
things?

Neil ⊥


Posted on the dev mailing list.