Abstract rewriting looks like a reasonable way to go, especially since it remains correct even if the language doesn't guarantee limit-of-knowledge evaluation. It may also make macros unnecessary.