paulstansifer / unseemly

Macros have types!
http://unseemly.github.io/
MIT License
129 stars 5 forks source link

Fix `pre_match`, somehow #13

Open paulstansifer opened 5 years ago

paulstansifer commented 5 years ago

There's something wrong with pre_match; I just wish I knew what.

For starters, it's named after when it gets called, not what it does. But mainly, everything associated with it is kinda a mess.

match_dotdotdot should really be recursively calling walk directly, so that it doesn't have to violate our principles and edit user code before checking it. (I'm not totally sure this is possible; it's kinda operating in the middle of an EnvMBE; can we call walk under those circumstances?)

Also, we have an unsettling workaround at the beginning of ast_walk to avoid calling pre_match under some circumstances that I no longer really understand:

    let (a, walk_ctxt) = match *a {
      // HACK: We want to process EE before pre_match before everything else.
      // This probably means we should find a way to get rid of pre_match.
      // But we can't just swap `a` and the ctxt when `a` is LiteralLike and the ctxt isn't.

      ExtendEnv(_,_) => { (a.clone(), walk_ctxt.clone()) }
      _ => Mode::D::pre_walk(a.clone(), walk_ctxt.clone())
    };

I think that the solution may to be to extend get_walk_rule to be able to look at the context, too (and maybe to have, in addition to Custom, a CustomThenRewalk or something). I have not thought this through.

paulstansifer commented 4 years ago

match_dotdotdot is now gone. I had to change the semantics of dotdotdots (now they are always tuples, rather than working inside any kind of repeated construct) to avoid needing to do a prematch for positive walks as well as negative ones.

paulstansifer commented 4 years ago

(In ccead10, I restored the old semantics of dotdotdot, but without using pre_match. On the other hand, I introduced something else to ast_walk::walk that is in obvious need of refactoring...)

paulstansifer commented 3 years ago

I wonder if, instead of immediately doing the "push-through" in pre_match, we could just have the walk result in a variable (or underdeterminedness) equalling some other thing, and outside the whole walk we recursively re-walk until we resolve all variables (or underdeterminednesses). Maybe then we could get rid of pre-matching?