Refactor: GitCommand is a ShellCommand
Forward interrupts to child processes.

When there's a long running child process (any Git command that uses a
pager, `!vim`, etc.) then any interrupt signal should be forwarded to the
child process, rather than handled by gitsh. If gitsh handles the signal it
will request a new line of input from the user, and interfere with the child
process, leaving the terminal in a confused state.

This interrupt forwarding needs to be recursive, in order to handle multiple
interrupts while running a child process that doesn't terminate on SIGINT.