Having it in the alias pass was slightly more efficient (finding expression roots has to be done in both passes), but further muddled up the already complex alias checker. Also factors out some duplication in the mutability-checking code.
This changes the indexing syntax from .() to [], the vector syntax from ~[] to [] and the extension syntax from #fmt() to #fmt[]