LinuxでPython

1.LinuxでPython

(1)インストールなど

①インストール
yum -y install python3
※Centos7だと、デフォルトでPython2がインストールされていると思う。

②バージョンの確認
python3 --version
Python 3.6.8

③Pythonの実行。対話モード(おそらくintructive)で実験 ※ある意味電卓のように使える。
[root@localhost user]# python3
>>> 1+2
3

このように、プログラムが動いてくれる。
対話モードを抜けるには
exit()

(2)対話モードで動かしてみる

①Pythonの起動
#python3
>>> 
②四則演算の実行
>>> 1+3
4
③抜ける
>>>quit()

④CTF問題。配列を降順に並び替える
https://ctf.cpaw.site/questions.php?qnum=14

単純化して、[15,1,93,52,66,3]を降順に並べ替えたいと思う。

# python3
>>> a=[15,1,93,52,66,3]  ←aという配列に値を入れる
>>> a.sort()    ←ソートする(昇順)
>>> print(a)
[1, 3, 15, 52, 66, 93]
>>> a.reverse()   ←降順に並べ替え
>>> print(a)
[93, 66, 52, 15, 3, 1]
>>> b=map(str,a)   ←数字はこのあとのjoinが使えないので、文字に変換
>>> c=''.join(b)  ←結合して結合した間には''として何も入れない
>>> print(c)   
9366521531  ←CTFの目的の結果が得られた。

(3)LinuxOS上で実施する場合

・拡張子は .py にするのが慣例。だけど、冒頭にシーバンと言われるおまじないのようなパスを入れると、拡張子が無くても実行できる。
・始めにおまじないとして、パスを入れる
#!/bin/python
↑だと、古いバージョンpython2点台が動く気がする。python2と3では、たとえば、printの書き方も変わっている。
#!/bin/python3
→以下、whichの実行例、/bin/python3が正しいような気がする。

# which python
/bin/python
# which python3
/bin/python3

文字コードでエラーが出る場合があるので、以下も入れておく。
# -*- coding: utf-8 -*-

#!/usr/bin/python3.7
# -*- coding: utf-8 -*-
print('hello')

2.PythonでLinuxのbashを動かす

・subprocessをimportする。
・いろいろなメソッドが用意されているが、たとえば、callは実行できたかを0か1で返す。
・実際には、生のコマンド結果を見たいだろうから、check_outputのメソッドを使う。
・このとき、半角スペースごとにコマンドは配列に入れて、['ls','-la']のようにリストにする。またはSplitで分ける。
・decode()を入れておくと、結果が改行されて普通に見ることができる。

(1)単純にlsコマンドを実行して、表示する

書き方はいくつかあるので、順番に。
❶単にコマンドを実行させるだけなら、以下。

#!/usr/bin/python3.7
import subprocess
subprocess.call('ls')

実際にLinux上でコマンドを打った時と同じように表示される。

a.txt  b.txt

❷違う書き方。

#!/usr/bin/python3.7
# -*- coding: utf-8 -*-
import subprocess
x=subprocess.check_output('ls')
print(x.decode())

こちらは表示方法が少し異なる。最後に空白行も残る。

a.txt  
b.txt
 
(2)ls -la のように、スペースを入れて引数を渡す場合

配列に入れる必要がある。
❶配列にして実行

#!/usr/bin/python3.7
import subprocess
subprocess.call(['ls','-la'])

❷配列に入れずに、splitで配列化
これが以外に楽かも。

#!/usr/bin/python3.7
import subprocess
x='ping -c 3 8.8.8.8'.split(' ')
subprocess.call(x)

❸他にも、配列に入れずに、shell=Trueをつけてもいい
ただ、注意すべき点があったはず。非推奨だと思う。

#!/usr/bin/python3.7
import subprocess
subprocess.call('ls -la',shell=True)

❹違う書き方。
以下の場合は、decode()を入れないと結果が改行されない。

#!/usr/bin/python3.7
import subprocess
print(subprocess.check_output(['ls','-la']).decode())

上記で、コマンドをcmdとして切り出してもいい。

#!/usr/bin/python3.7
import subprocess
cmd=['ls','-la']
print(subprocess.check_output(cmd).decode())
(3)ユーザをループで作ってみよう

pythonを使うと、ループ処理などができる。(まあ、bashでもできるけど)
そうであれば、ユーザを一気に作ったりとか、権限を変更したりなどが簡単にできる。
以下はuseraddでuser0からuser2までを作る。

#!/usr/bin/python3.7
import subprocess

for i in range(3):
    cmd="useradd user%s" % i
    result = subprocess.check_output(cmd, shell=True)

subprocessを使うのであるが、メソッドにはいくつかあり、check_outputが便利らしい。
https://qiita.com/ichiroex/items/681936b7711121d0a360
ただ、上記の場合、ログはうまく表示されなかったが、ユーザは適切に作ることができた。
result に入れて、print(result)をすれば、結果がうまくけば0が表示されるので、確認にはいいかもしれない。
・以下は、ユーザとパスワードを作成するところまで。たとえば、g1_userのパスワードはpass1である。

#!/usr/bin/python3.7
import subprocess
for i in range(1,3):
    cmd1="useradd g%s_user" % i
    cmd2="echo pass%s | passwd --stdin g%s_user" %(i,i)

    result1 = subprocess.call(cmd1, shell=True)
    result2 = subprocess.call(cmd2, shell=True)
    print(result1);print(result2)

※コマンドを複数つなげる方法は不明。単にbashのコマンドを書くときに、&でつなげてもいいだろう。
※reslut のところはcmd=[cmd1,cmd2]とリストにして、for j in cmdでリストで回してみた。だけど、同じことを実行しているのに、なぜかリストで回すとbashがエラーになったので、やめた。