When we used size_t/ssize_t they conflicted with the system's word sized
integers. This should work well for all the numeric types we're likely
to see.
These safely cast between signed and unsigned numeric quantities,
aborting if the result cannot be safely converted (as opposed to size
expanding or throwing).