Instead of passing function pointers, we're passing structs with context
now. The idea is the same, I/O functions require some struct with a
function pointer and some generic memory that only the output device
cares about. I/O just calls it.
VGA has been reworked to accomodate this change, as well as default
outputs being created for low-overhead use (such as interrupt handlers).