ligne de shebang ne fonctionne pas avec cr-lf


10

Pourquoi les parties shebang des scripts élémentaires suivants ne fonctionnent-elles pas:

$ cat hello.sh
#! /bin/sh
echo Hello
$ ./hello.sh
bash: ./hello.sh: /bin/sh^M: bad interpreter: No such file or directory

$ cat hello.py
#! /usr/bin/env python3
print("Hello")
$ ./hello.py
: No such file or directory

alors que l'appel manuel de l'interpréteur fonctionne:

$ sh hello.sh
Hello
$ python3 hello.py
Hello

Réponses:


11

Vos scripts ont probablement des fins de ligne CR-LF de style DOS et non des fins de ligne LF de style Unix. Le ^ M vu dans le message d'erreur dans le premier cas est une indication que le caractère 0D a été interprété comme faisant partie du nom de l'interpréteur de script et non pas comme faisant partie de la fin de ligne (comme on pourrait s'y attendre). Puisqu'il n'y a pas de fichier exécutable sur votre système avec un chemin qui inclut le caractère 0D (^ M), le système n'est pas en mesure d'appeler l'interpréteur. Lorsque vous appelez manuellement votre interprète, il est capable de gérer les deux types de fins de ligne présents dans le script.

Si vous convertissez les scripts pour utiliser des fins de ligne LF de style Unix, vous devriez voir le shebang fonctionner. Lisez la suite pour une illustration.

Dans la session ci-dessous, todos et fromdos sont un utilitaire (disponible sur Ubuntu en tant que package tofrodos) pour convertir les conventions de fin de ligne de CR-LF en LF. Tout utilitaire équivalent (voir cette question unix.SE ) le ferait à des fins de démonstration.

La transcription de session suivante (exécutée avec vos mêmes fichiers de script) devrait clarifier la situation:

$ fromdos hello.sh
$ ./hello.sh
Hello
$ todos hello.sh
$ ./hello.sh
bash: ./hello.sh: /bin/sh^M: bad interpreter: No such file or directory
$
$ fromdos hello.py
$ ./hello.py
Hello
$ todos hello.py
$ ./hello.py
: No such file or directory
$

Il semble que c'est le noyau qui lit la ligne shebang, et apparemment le noyau Linux (au moins à partir de la version sur mon système Kubuntu Saucy) ne reconnaît pas le CR dans le cadre de la convention de fin de ligne CR-LF.

Si le shebang de votre script ne semble pas fonctionner (c'est-à-dire appeler manuellement l'interpréteur sur le script fonctionne mais vous ne pouvez pas exécuter le script en utilisant son nom de fichier même si vous l'avez fait chmod +x), alors c'est une raison possible.

REMARQUE: Merci aux autres qui ont également commenté. Je serais également heureux d'entendre s'il y a de meilleures réponses!

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.