import sys
import os
import pty
import select
def main():
(pid, fd) = pty.fork()
if pid == -1:
print "Couldn't fork"
sys.exit(1)
if pid == 0: # child process
os.execvp('telnet', ('telnet','localhost',))
# parent process
while 1:
delay = 1
(r,w,e) = select.select( [sys.stdin.fileno(), fd], [], [],
delay)
for File in r:
if File == sys.stdin.fileno():
#from_user = sys.stdin.read()
#from_user = sys.stdin.raw_input()
from_user = os.read( 0, 1024)
print "user input:"+from_user
if from_user == "q": break
#os.write( fd, from_user )
if File == fd:
from_telnet = os.read(fd, 1024)
sys.stdout.write( from_telnet )
if __name__ == '__main__': main()
---------------------------
Sent via Deja.com http://www.deja.com/
Before you buy.
| I am a newbie to python and try to write a middle layer
| between the telnet and rxvt to provide some special analyse function. I
| use the select module to listen on the stdin and pty-master-end which
| connected with the telnet. but the select statement seems blocked when
| the string passed from telnet not ended with a NewLine character. I
| have searched the archive but chould not find the answer, can you give
| me a help? thanks!
The UNIX terminal driver is a line oriented device, it holds on to
your input line so that it can process backspaces and things like
that. If you want your program to see input immediately and directly,
you can turn this feature off, with the POSIX terminal control functions.
Afterwards, put it back the way it was!
Your program is appended, modified to do this. For more information on
the tty control bits, check your man pages. On my host that's
"man 4 termios", but the location varies from one platform to another.
Donn Cave, do...@u.washington.edu
----------------------------------------
#!/usr/bin/env python
import sys
import os
import pty
import select
import termios
import TERMIOS
def main():
(pid, fd) = pty.fork()
# Python won't return -1, rather will raise exception.
if pid == 0: # child process
try:
os.execvp('telnet', ('telnet','localhost',))
except:
# must not return to caller.
os._exit(0)
# parent process
iflag, oflag, cflag, lflag, ispeed, ospeed, cc = termios.tcgetattr(0)
lflag = lflag
raw_lflag = lflag & ~(TERMIOS.ICANON|TERMIOS.ECHO)
raw_iflag = iflag & ~(TERMIOS.ICRNL)
raw_cc = cc[:]
raw_cc[TERMIOS.VMIN] = 1
raw_cc[TERMIOS.VTIME] = 0
termios.tcsetattr(0, TERMIOS.TCSANOW, [raw_iflag, oflag, cflag,
raw_lflag, ispeed, ospeed, raw_cc])
try:
while 1:
delay = 1
from_user = ''
(r,w,e) = select.select([0, fd], [], [], delay)
for File in r:
if File == 0:
from_user = os.read(0, 1024)
# print 'user input:', repr(from_user)
os.write(fd, from_user)
if File == fd:
from_telnet = os.read(fd, 1024)
os.write(1, from_telnet)
if from_user == 'q':
break
except:
termios.tcsetattr(0, TERMIOS.TCSANOW, [iflag, oflag, cflag,
lflag, ispeed, ospeed, cc])
raise
termios.tcsetattr(0, TERMIOS.TCSANOW, [iflag, oflag, cflag,
lflag, ispeed, ospeed, cc])
if __name__ == '__main__':
main()
---------- Bonus version --------------
#!/usr/bin/env python
import sys
import os
import pty
import select
import termios
import TERMIOS
class TTY:
def __init__(self):
self.iflag, self.oflag, self.cflag, self.lflag, \
self.ispeed, self.ospeed, self.cc = termios.tcgetattr(0)
def raw(self):
raw_lflag = self.lflag & ~(TERMIOS.ICANON|TERMIOS.ECHO)
raw_iflag = self.iflag & ~(TERMIOS.ICRNL)
raw_cc = self.cc[:]
raw_cc[TERMIOS.VMIN] = 1
raw_cc[TERMIOS.VTIME] = 0
termios.tcsetattr(0, TERMIOS.TCSANOW, [raw_iflag, self.oflag,
self.cflag, raw_lflag, self.ispeed, self.ospeed,
raw_cc])
def restore(self):
termios.tcsetattr(0, TERMIOS.TCSANOW, [self.iflag, self.oflag,
self.cflag, self.lflag, self.ispeed, self.ospeed,
self.cc])
def main():
pid, fd = pty.fork()
# Python won't return -1, rather will raise exception.
if pid == 0: # child process
try:
os.execvp('telnet', ('telnet','localhost',))
except:
# must not return to caller.
os._exit(0)
# parent process
input = TTY()
input.raw()
try:
while 1:
delay = 1
from_user = ''
r, w, e = select.select([0, fd], [], [], delay)
for File in r:
if File == 0:
from_user = os.read(0, 1024)
# print 'user input:', repr(from_user)
os.write(fd, from_user)
if File == fd:
from_telnet = os.read(fd, 1024)
os.write(1, from_telnet)
if from_user == 'q':
break
except:
input.restore()
raise
input.restore()