symbian-qemu-0.9.1-12/python-2.6.1/Demo/tkinter/guido/ShellWindow.py
changeset 1 2fb8b9db1c86
equal deleted inserted replaced
0:ffa851df0825 1:2fb8b9db1c86
       
     1 import os
       
     2 import sys
       
     3 import string
       
     4 from Tkinter import *
       
     5 from ScrolledText import ScrolledText
       
     6 from Dialog import Dialog
       
     7 import signal
       
     8 
       
     9 BUFSIZE = 512
       
    10 
       
    11 class ShellWindow(ScrolledText):
       
    12 
       
    13     def __init__(self, master=None, shell=None, **cnf):
       
    14         if not shell:
       
    15             try:
       
    16                 shell = os.environ['SHELL']
       
    17             except KeyError:
       
    18                 shell = '/bin/sh'
       
    19             shell = shell + ' -i'
       
    20         args = string.split(shell)
       
    21         shell = args[0]
       
    22 
       
    23         apply(ScrolledText.__init__, (self, master), cnf)
       
    24         self.pos = '1.0'
       
    25         self.bind('<Return>', self.inputhandler)
       
    26         self.bind('<Control-c>', self.sigint)
       
    27         self.bind('<Control-t>', self.sigterm)
       
    28         self.bind('<Control-k>', self.sigkill)
       
    29         self.bind('<Control-d>', self.sendeof)
       
    30 
       
    31         self.pid, self.fromchild, self.tochild = spawn(shell, args)
       
    32         self.tk.createfilehandler(self.fromchild, READABLE,
       
    33                                   self.outputhandler)
       
    34 
       
    35     def outputhandler(self, file, mask):
       
    36         data = os.read(file, BUFSIZE)
       
    37         if not data:
       
    38             self.tk.deletefilehandler(file)
       
    39             pid, sts = os.waitpid(self.pid, 0)
       
    40             print 'pid', pid, 'status', sts
       
    41             self.pid = None
       
    42             detail = sts>>8
       
    43             cause = sts & 0xff
       
    44             if cause == 0:
       
    45                 msg = "exit status %d" % detail
       
    46             else:
       
    47                 msg = "killed by signal %d" % (cause & 0x7f)
       
    48                 if cause & 0x80:
       
    49                     msg = msg + " -- core dumped"
       
    50             Dialog(self.master,
       
    51                    text=msg,
       
    52                    title="Exit status",
       
    53                    bitmap='warning',
       
    54                    default=0,
       
    55                    strings=('OK',))
       
    56             return
       
    57         self.insert(END, data)
       
    58         self.pos = self.index("end - 1 char")
       
    59         self.yview_pickplace(END)
       
    60 
       
    61     def inputhandler(self, *args):
       
    62         if not self.pid:
       
    63             self.no_process()
       
    64             return "break"
       
    65         self.insert(END, "\n")
       
    66         line = self.get(self.pos, "end - 1 char")
       
    67         self.pos = self.index(END)
       
    68         os.write(self.tochild, line)
       
    69         return "break"
       
    70 
       
    71     def sendeof(self, *args):
       
    72         if not self.pid:
       
    73             self.no_process()
       
    74             return "break"
       
    75         os.close(self.tochild)
       
    76         return "break"
       
    77 
       
    78     def sendsig(self, sig):
       
    79         if not self.pid:
       
    80             self.no_process()
       
    81             return "break"
       
    82         os.kill(self.pid, sig)
       
    83         return "break"
       
    84 
       
    85     def sigint(self, *args):
       
    86         return self.sendsig(signal.SIGINT)
       
    87 
       
    88     def sigquit(self, *args):
       
    89         return self.sendsig(signal.SIGQUIT)
       
    90 
       
    91     def sigterm(self, *args):
       
    92         return self.sendsig(signal.SIGTERM)
       
    93 
       
    94     def sigkill(self, *args):
       
    95         return self.sendsig(signal.SIGKILL)
       
    96 
       
    97     def no_process(self):
       
    98         Dialog(self.master,
       
    99                text="No active process",
       
   100                title="No process",
       
   101                bitmap='error',
       
   102                default=0,
       
   103                strings=('OK',))
       
   104 
       
   105 MAXFD = 100     # Max number of file descriptors (os.getdtablesize()???)
       
   106 
       
   107 def spawn(prog, args):
       
   108     p2cread, p2cwrite = os.pipe()
       
   109     c2pread, c2pwrite = os.pipe()
       
   110     pid = os.fork()
       
   111     if pid == 0:
       
   112         # Child
       
   113         for i in 0, 1, 2:
       
   114             try:
       
   115                 os.close(i)
       
   116             except os.error:
       
   117                 pass
       
   118         if os.dup(p2cread) <> 0:
       
   119             sys.stderr.write('popen2: bad read dup\n')
       
   120         if os.dup(c2pwrite) <> 1:
       
   121             sys.stderr.write('popen2: bad write dup\n')
       
   122         if os.dup(c2pwrite) <> 2:
       
   123             sys.stderr.write('popen2: bad write dup\n')
       
   124         os.closerange(3, MAXFD)
       
   125         try:
       
   126             os.execvp(prog, args)
       
   127         finally:
       
   128             sys.stderr.write('execvp failed\n')
       
   129             os._exit(1)
       
   130     os.close(p2cread)
       
   131     os.close(c2pwrite)
       
   132     return pid, c2pread, p2cwrite
       
   133 
       
   134 def test():
       
   135     shell = string.join(sys.argv[1:])
       
   136     root = Tk()
       
   137     root.minsize(1, 1)
       
   138     if shell:
       
   139         w = ShellWindow(root, shell=shell)
       
   140     else:
       
   141         w = ShellWindow(root)
       
   142     w.pack(expand=1, fill=BOTH)
       
   143     w.focus_set()
       
   144     w.tk.mainloop()
       
   145 
       
   146 if __name__ == '__main__':
       
   147     test()