Migrate std::fmt to core::fmt

This was a more difficult change than I thought it would be, and it is unfortunately a breaking change rather than a drop-in replacement. Most of the rationale can be found in the third commit.