1. cielavenir

    No comment

    cielavenir
Changes in body
Source | HTML | Preview
@@ -1,54 +1,55 @@
※本記事の内容はWindowsには一切当てはまりません。
https://linuxjm.osdn.jp/html/LDP_man-pages/man3/exec.3.html 等によると、execvpでのみ、ENOEXECが発生したらシェルスクリプトと解釈する機能があるそうです。
スクリプト言語でシェルを使わず外部プログラムを実行した場合、この機能は働くのでしょうか?
## 準備
```
$ cat lsscript
ls
```
## 実行
### Ruby
-- 直接実行(例): popenの引数が配列
+- 直接実行(例): popenの引数が配列、systemの引数が2要素以上
- `ruby -e 'p IO.popen(["./lsscript"]).read'`
process.c proc_exec_cmd
execveを試し、ENOEXECなら/bin/shを付加して再試行
### Python
- 直接実行(例): check_call(等)の引数が配列
- `python -c 'import subprocess;subprocess.check_call(["./lsscript"])'`
Modules/_posixsubprocess.c child_exec
execveを試す。 **ENOEXECの場合失敗する**
Python3も同様。
なおshell=Trueとすると失敗しなくなりますがpipes.quoteやらshlex.quoteやらが必要となります。
+(この記事の読者であればこちらの必要性はわかりますよね)
### Perl
-- 直接実行(例): system()の引数が2以上
+- 直接実行(例): system()の引数が2要素以上
- `perl -e 'print system("./lsscript","dummy")'`
doio.c Perl_do_aexec5
execvpを試す。
### PHP
- 直接実行: pcntl_exec
- `php -r 'pcntl_exec("./lsscript");'`
ext/pcntl/pcntl.c pcntl_exec
execveを試す。 **ENOEXECの場合失敗する**
(上はexecですからサブプロセスとするにはfork呼び出し等が必要。その辺が必要ない標準実行系はext/standard/exec.cにありますが、popen固定のようです(つまり必ずシェルが入る))
## 結論
Python/PHPでシェルを介さずに実行しようとすると、自動でshを付けてくれません。[C言語のshebangもどき](https://qiita.com/cielavenir/items/6063c117f25f9188b84c)等を投げる際はご注意ください。