1
2

More than 5 years have passed since last update.

端末をRAWモードに設定して子プロセスに制御文字を素通りさせる

Last updated at Posted at 2017-01-04

sshクライアントみたいなプログラムをどうやったらつくれるのか知りたかったので、とりあえずローカルでforkしたプロセスをラップするだけのプログラムをつくってみた。

Python版

PTYの扱いがいまいちわからなかったので、PtyProcessというライブラリを使ってずるをした。

import sys
import tty
import os
import termios
import select
import ptyprocess
import threading
import time

stop_event = threading.Event()

def read_stdin(p):
    while not stop_event.is_set():
        r, w, e = select.select([sys.stdin], [], [], 0)
        #print('hoge')
        if sys.stdin in r:
            x = sys.stdin.read(1)
            p.write(x)
        time.sleep(0.01)

#args = ['python']
args = ['bash']
p = ptyprocess.PtyProcessUnicode.spawn(args)
t = threading.Thread(target=read_stdin, args=(p,))
t.start()

oldtty = termios.tcgetattr(sys.stdin)

tty.setraw(sys.stdin.fileno())
print("raw mode started")
tty.setcbreak(sys.stdin.fileno())
print("cbreak mode started")

while True:
    try:
        x = p.read(1)
        sys.stdout.write(x)
        sys.stdout.flush()
    except EOFError:
        print("subprocess exit")
        break

stop_event.set()
t.join()

termios.tcsetattr(sys.stdin, termios.TCSADRAIN, oldtty)

http://www.betatechnology.jp/pp/index.php?Unix%2F%E7%AB%AF%E6%9C%AB
http://docs.python.jp/3/library/pty.html
http://docs.python.jp/3.5/library/termios.html
http://docs.python.jp/3.5/library/tty.html

Ruby版

rubyでもやってみた

require "pty"
require "termios"

STDIN.extend Termios
term_preset = STDIN.tcgetattr

system("stty raw -echo")

begin
  PTY.spawn("bash -i") do |pin, pout|
    Thread.new do
      loop do
        pout.print STDIN.getc.chr
      end
    end

    loop do
      print pin.sysread(512)
      STDOUT.flush
    end
  end
rescue EOFError => e
  STDIN.tcsetattr(Termios::TCSANOW, term_preset)
end

termiosはgem install ruby-termiosでインストールできる。

http://stackoverflow.com/questions/2730642/wrapper-around-bash-control-stdin-and-stdout
http://melborne.github.io/2013/02/19/flippy-console-now-added/

1
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
2