Você está certo: o redirecionamento para fluxos de entrada e saída é feito pelo shell.
Mais detalhadamente, quando você executa um comando através do shell, o seguinte procedimento é executado:
-
Os garfos do shell criam um novo processo.
-
O shell recém-criado (shell "filho") aplica redirecionamentos: abre o arquivo especificado como destino de saída (resp. fonte de entrada) e define como o novo fluxo STDOUT (resp. STDIN) (usando o chamada do sistema dup2 .
-
O shell "child" executa o comando que você pediu para executar, usando o execve (2) chamada de sistema, que substitui o processo do shell por um novo programa.