Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(503)

Side by Side Diff: third_party/pexpect/examples/cgishell.cgi

Issue 1398903002: Add third_party/pexpect (Closed) Base URL: https://chromium.googlesource.com/crashpad/crashpad@end-to-end-test
Patch Set: Created 5 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « third_party/pexpect/examples/astat.py ('k') | third_party/pexpect/examples/chess.py » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 #!/usr/bin/python
2 ##!/usr/bin/env python
3 """CGI shell server
4
5 This exposes a shell terminal on a web page.
6 It uses AJAX to send keys and receive screen updates.
7 The client web browser needs nothing but CSS and Javascript.
8
9 --hostname : sets the remote host name to open an ssh connection to.
10 --username : sets the user name to login with
11 --password : (optional) sets the password to login with
12 --port : set the local port for the server to listen on
13 --watch : show the virtual screen after each client request
14
15 This project is probably not the most security concious thing I've ever built.
16 This should be considered an experimental tool -- at best.
17 """
18
19 from __future__ import absolute_import
20 from __future__ import print_function
21
22 import sys,os
23 sys.path.insert (0,os.getcwd()) # let local modules precede any installed module s
24 import socket, random, string, traceback, cgi, time, getopt, getpass, threading, resource, signal
25 import pxssh, pexpect, ANSI
26
27 def exit_with_usage(exit_code=1):
28 print(globals()['__doc__'])
29 os._exit(exit_code)
30
31 def client (command, host='localhost', port=-1):
32 """This sends a request to the server and returns the response.
33 If port <= 0 then host is assumed to be the filename of a Unix domain socket .
34 If port > 0 then host is an inet hostname.
35 """
36 if port <= 0:
37 s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
38 s.connect(host)
39 else:
40 s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
41 s.connect((host, port))
42 s.send(command)
43 data = s.recv (2500)
44 s.close()
45 return data
46
47 def server (hostname, username, password, socket_filename='/tmp/server_sock', da emon_mode = True, verbose=False):
48 """This starts and services requests from a client.
49 If daemon_mode is True then this forks off a separate daemon process and returns the daemon's pid.
50 If daemon_mode is False then this does not return until the server is do ne.
51 """
52 if daemon_mode:
53 mypid_name = '/tmp/%d.pid' % os.getpid()
54 daemon_pid = daemonize(daemon_pid_filename=mypid_name)
55 time.sleep(1)
56 if daemon_pid != 0:
57 os.unlink(mypid_name)
58 return daemon_pid
59
60 virtual_screen = ANSI.ANSI (24,80)
61 child = pxssh.pxssh()
62 try:
63 child.login (hostname, username, password, login_naked=True)
64 except:
65 return
66 if verbose: print('login OK')
67 virtual_screen.write (child.before)
68 virtual_screen.write (child.after)
69
70 if os.path.exists(socket_filename): os.remove(socket_filename)
71 s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
72 s.bind(socket_filename)
73 os.chmod(socket_filename, 0o777)
74 if verbose: print('Listen')
75 s.listen(1)
76
77 r = roller (endless_poll, (child, child.PROMPT, virtual_screen))
78 r.start()
79 if verbose: print("started screen-poll-updater in background thread")
80 sys.stdout.flush()
81 try:
82 while True:
83 conn, addr = s.accept()
84 if verbose: print('Connected by', addr)
85 data = conn.recv(1024)
86 request = data.split(' ', 1)
87 if len(request)>1:
88 cmd = request[0].strip()
89 arg = request[1].strip()
90 else:
91 cmd = request[0].strip()
92 arg = ''
93
94 if cmd == 'exit':
95 r.cancel()
96 break
97 elif cmd == 'sendline':
98 child.sendline (arg)
99 time.sleep(0.1)
100 shell_window = str(virtual_screen)
101 elif cmd == 'send' or cmd=='xsend':
102 if cmd=='xsend':
103 arg = arg.decode("hex")
104 child.send (arg)
105 time.sleep(0.1)
106 shell_window = str(virtual_screen)
107 elif cmd == 'cursor':
108 shell_window = '%x,%x' % (virtual_screen.cur_r, virtual_screen.c ur_c)
109 elif cmd == 'refresh':
110 shell_window = str(virtual_screen)
111 elif cmd == 'hash':
112 shell_window = str(hash(str(virtual_screen)))
113
114 response = []
115 response.append (shell_window)
116 if verbose: print('\n'.join(response))
117 sent = conn.send('\n'.join(response))
118 if sent < len (response):
119 if verbose: print("Sent is too short. Some data was cut off.")
120 conn.close()
121 except e:
122 pass
123 r.cancel()
124 if verbose: print("cleaning up socket")
125 s.close()
126 if os.path.exists(socket_filename): os.remove(socket_filename)
127 if verbose: print("server done!")
128
129 class roller (threading.Thread):
130 """This class continuously loops a function in a thread.
131 This is basically a thin layer around Thread with a
132 while loop and a cancel.
133 """
134 def __init__(self, function, args=[], kwargs={}):
135 threading.Thread.__init__(self)
136 self.function = function
137 self.args = args
138 self.kwargs = kwargs
139 self.finished = threading.Event()
140 def cancel(self):
141 """Stop the roller."""
142 self.finished.set()
143 def run(self):
144 while not self.finished.isSet():
145 self.function(*self.args, **self.kwargs)
146
147 def endless_poll (child, prompt, screen, refresh_timeout=0.1):
148 """This keeps the screen updated with the output of the child.
149 This will be run in a separate thread. See roller class.
150 """
151 #child.logfile_read = screen
152 try:
153 s = child.read_nonblocking(4000, 0.1)
154 screen.write(s)
155 except:
156 pass
157
158 def daemonize (stdin=None, stdout=None, stderr=None, daemon_pid_filename=None):
159 """This runs the current process in the background as a daemon.
160 The arguments stdin, stdout, stderr allow you to set the filename that the d aemon reads and writes to.
161 If they are set to None then all stdio for the daemon will be directed to /d ev/null.
162 If daemon_pid_filename is set then the pid of the daemon will be written to it as plain text
163 and the pid will be returned. If daemon_pid_filename is None then this will return None.
164 """
165 UMASK = 0
166 WORKINGDIR = "/"
167 MAXFD = 1024
168
169 # The stdio file descriptors are redirected to /dev/null by default.
170 if hasattr(os, "devnull"):
171 DEVNULL = os.devnull
172 else:
173 DEVNULL = "/dev/null"
174 if stdin is None: stdin = DEVNULL
175 if stdout is None: stdout = DEVNULL
176 if stderr is None: stderr = DEVNULL
177
178 try:
179 pid = os.fork() # fork first child
180 except OSError as e:
181 raise Exception("%s [%d]" % (e.strerror, e.errno))
182
183 if pid != 0:
184 os.waitpid(pid,0)
185 if daemon_pid_filename is not None:
186 daemon_pid = int(file(daemon_pid_filename,'r').read())
187 return daemon_pid
188 else:
189 return None
190
191 # first child
192 os.setsid()
193 signal.signal(signal.SIGHUP, signal.SIG_IGN)
194
195 try:
196 pid = os.fork() # fork second child
197 except OSError as e:
198 raise Exception("%s [%d]" % (e.strerror, e.errno))
199
200 if pid != 0:
201 if daemon_pid_filename is not None:
202 file(daemon_pid_filename,'w').write(str(pid))
203 os._exit(0) # exit parent (the first child) of the second child.
204
205 # second child
206 os.chdir(WORKINGDIR)
207 os.umask(UMASK)
208
209 maxfd = resource.getrlimit(resource.RLIMIT_NOFILE)[1]
210 if maxfd == resource.RLIM_INFINITY:
211 maxfd = MAXFD
212
213 # close all file descriptors
214 for fd in range(0, maxfd):
215 try:
216 os.close(fd)
217 except OSError: # fd wasn't open to begin with (ignored)
218 pass
219
220 os.open (DEVNULL, os.O_RDWR) # standard input
221
222 # redirect standard file descriptors
223 si = open(stdin, 'r')
224 so = open(stdout, 'a+')
225 se = open(stderr, 'a+', 0)
226 os.dup2(si.fileno(), sys.stdin.fileno())
227 os.dup2(so.fileno(), sys.stdout.fileno())
228 os.dup2(se.fileno(), sys.stderr.fileno())
229
230 return 0
231
232 def client_cgi ():
233 """This handles the request if this script was called as a cgi.
234 """
235 sys.stderr = sys.stdout
236 ajax_mode = False
237 TITLE="Shell"
238 SHELL_OUTPUT=""
239 SID="NOT"
240 print("Content-type: text/html;charset=utf-8\r\n")
241 try:
242 form = cgi.FieldStorage()
243 if 'ajax' in form:
244 ajax_mode = True
245 ajax_cmd = form['ajax'].value
246 SID=form['sid'].value
247 if ajax_cmd == 'send':
248 command = 'xsend'
249 arg = form['arg'].value.encode('hex')
250 result = client (command + ' ' + arg, '/tmp/'+SID)
251 print(result)
252 elif ajax_cmd == 'refresh':
253 command = 'refresh'
254 result = client (command, '/tmp/'+SID)
255 print(result)
256 elif ajax_cmd == 'cursor':
257 command = 'cursor'
258 result = client (command, '/tmp/'+SID)
259 print(result)
260 elif ajax_cmd == 'exit':
261 command = 'exit'
262 result = client (command, '/tmp/'+SID)
263 print(result)
264 elif ajax_cmd == 'hash':
265 command = 'hash'
266 result = client (command, '/tmp/'+SID)
267 print(result)
268 elif 'sid' not in form:
269 SID=random_sid()
270 print(LOGIN_HTML % locals());
271 else:
272 SID=form['sid'].value
273 if 'start_server' in form:
274 USERNAME = form['username'].value
275 PASSWORD = form['password'].value
276 dpid = server ('127.0.0.1', USERNAME, PASSWORD, '/tmp/'+SID)
277 SHELL_OUTPUT="daemon pid: " + str(dpid)
278 else:
279 if 'cli' in form:
280 command = 'sendline ' + form['cli'].value
281 else:
282 command = 'sendline'
283 SHELL_OUTPUT = client (command, '/tmp/'+SID)
284 print(CGISH_HTML % locals())
285 except:
286 tb_dump = traceback.format_exc()
287 if ajax_mode:
288 print(str(tb_dump))
289 else:
290 SHELL_OUTPUT=str(tb_dump)
291 print(CGISH_HTML % locals())
292
293 def server_cli():
294 """This is the command line interface to starting the server.
295 This handles things if the script was not called as a CGI
296 (if you run it from the command line).
297 """
298 try:
299 optlist, args = getopt.getopt(sys.argv[1:], 'h?d', ['help','h','?', 'hos tname=', 'username=', 'password=', 'port=', 'watch'])
300 except Exception as e:
301 print(str(e))
302 exit_with_usage()
303
304 command_line_options = dict(optlist)
305 options = dict(optlist)
306 # There are a million ways to cry for help. These are but a few of them.
307 if [elem for elem in command_line_options if elem in ['-h','--h','-?','--?', '--help']]:
308 exit_with_usage(0)
309
310 hostname = "127.0.0.1"
311 #port = 1664
312 username = os.getenv('USER')
313 password = ""
314 daemon_mode = False
315 if '-d' in options:
316 daemon_mode = True
317 if '--watch' in options:
318 watch_mode = True
319 else:
320 watch_mode = False
321 if '--hostname' in options:
322 hostname = options['--hostname']
323 if '--port' in options:
324 port = int(options['--port'])
325 if '--username' in options:
326 username = options['--username']
327 if '--password' in options:
328 password = options['--password']
329 else:
330 password = getpass.getpass('password: ')
331
332 server (hostname, username, password, '/tmp/mysock', daemon_mode)
333
334 def random_sid ():
335 a=random.randint(0,65535)
336 b=random.randint(0,65535)
337 return '%04x%04x.sid' % (a,b)
338
339 def parse_host_connect_string (hcs):
340 """This parses a host connection string in the form
341 username:password@hostname:port. All fields are options expcet hostname. A
342 dictionary is returned with all four keys. Keys that were not included are
343 set to empty strings ''. Note that if your password has the '@' character
344 then you must backslash escape it.
345 """
346 if '@' in hcs:
347 p = re.compile (r'(?P<username>[^@:]*)(:?)(?P<password>.*)(?!\\)@(?P<hos tname>[^:]*):?(?P<port>[0-9]*)')
348 else:
349 p = re.compile (r'(?P<username>)(?P<password>)(?P<hostname>[^:]*):?(?P<p ort>[0-9]*)')
350 m = p.search (hcs)
351 d = m.groupdict()
352 d['password'] = d['password'].replace('\\@','@')
353 return d
354
355 def pretty_box (s, rows=24, cols=80):
356 """This puts an ASCII text box around the given string.
357 """
358 top_bot = '+' + '-'*cols + '+\n'
359 return top_bot + '\n'.join(['|'+line+'|' for line in s.split('\n')]) + '\n' + top_bot
360
361 def main ():
362 if os.getenv('REQUEST_METHOD') is None:
363 server_cli()
364 else:
365 client_cgi()
366
367 # It's mostly HTML and Javascript from here on out.
368 CGISH_HTML="""<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
369 <html>
370 <head>
371 <title>%(TITLE)s %(SID)s</title>
372 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
373 <style type=text/css>
374 a {color: #9f9; text-decoration: none}
375 a:hover {color: #0f0}
376 hr {color: #0f0}
377 html,body,textarea,input,form
378 {
379 font-family: "Courier New", Courier, mono;
380 font-size: 8pt;
381 color: #0c0;
382 background-color: #020;
383 margin:0;
384 padding:0;
385 border:0;
386 }
387 input { background-color: #010; }
388 textarea {
389 border-width:1;
390 border-style:solid;
391 border-color:#0c0;
392 padding:3;
393 margin:3;
394 }
395 </style>
396
397 <script language="JavaScript">
398 function focus_first()
399 {if (document.forms.length > 0)
400 {var TForm = document.forms[0];
401 for (i=0;i<TForm.length;i++){
402 if ((TForm.elements[i].type=="text")||
403 (TForm.elements[i].type=="textarea")||
404 (TForm.elements[i].type.toString().charAt(0)=="s"))
405 {document.forms[0].elements[i].focus();break;}}}}
406
407 // JavaScript Virtual Keyboard
408 // If you like this code then buy me a sandwich.
409 // Noah Spurrier <noah@noah.org>
410 var flag_shift=0;
411 var flag_shiftlock=0;
412 var flag_ctrl=0;
413 var ButtonOnColor="#ee0";
414
415 function init ()
416 {
417 // hack to set quote key to show both single quote and double quote
418 document.form['quote'].value = "'" + ' "';
419 //refresh_screen();
420 poll();
421 document.form["cli"].focus();
422 }
423 function get_password ()
424 {
425 var username = prompt("username?","");
426 var password = prompt("password?","");
427 start_server (username, password);
428 }
429 function multibrowser_ajax ()
430 {
431 var xmlHttp = false;
432 /*@cc_on @*/
433 /*@if (@_jscript_version >= 5)
434 try
435 {
436 xmlHttp = new ActiveXObject("Msxml2.XMLHTTP");
437 }
438 catch (e)
439 {
440 try
441 {
442 xmlHttp = new ActiveXObject("Microsoft.XMLHTTP");
443 }
444 catch (e2)
445 {
446 xmlHttp = false;
447 }
448 }
449 @end @*/
450
451 if (!xmlHttp && typeof XMLHttpRequest != 'undefined')
452 {
453 xmlHttp = new XMLHttpRequest();
454 }
455 return xmlHttp;
456 }
457 function load_url_to_screen(url)
458 {
459 xmlhttp = multibrowser_ajax();
460 //window.XMLHttpRequest?new XMLHttpRequest(): new ActiveXObject("Microsoft.X MLHTTP");
461 xmlhttp.onreadystatechange = update_virtual_screen;
462 xmlhttp.open("GET", url);
463 xmlhttp.setRequestHeader("If-Modified-Since", "Sat, 1 Jan 2000 00:00:00 GMT" );
464 xmlhttp.send(null);
465 }
466 function update_virtual_screen()
467 {
468 if ((xmlhttp.readyState == 4) && (xmlhttp.status == 200))
469 {
470 var screen_text = xmlhttp.responseText;
471 document.form["screen_text"].value = screen_text;
472 //var json_data = json_parse(xmlhttp.responseText);
473 }
474 }
475 function poll()
476 {
477 refresh_screen();
478 timerID = setTimeout("poll()", 2000);
479 // clearTimeout(timerID);
480 }
481 //function start_server (username, password)
482 //{
483 // load_url_to_screen('cgishell.cgi?ajax=serverstart&username=' + escape(user name) + '&password=' + escape(password);
484 //}
485 function refresh_screen()
486 {
487 load_url_to_screen('cgishell.cgi?ajax=refresh&sid=%(SID)s');
488 }
489 function query_hash()
490 {
491 load_url_to_screen('cgishell.cgi?ajax=hash&sid=%(SID)s');
492 }
493 function query_cursor()
494 {
495 load_url_to_screen('cgishell.cgi?ajax=cursor&sid=%(SID)s');
496 }
497 function exit_server()
498 {
499 load_url_to_screen('cgishell.cgi?ajax=exit&sid=%(SID)s');
500 }
501 function type_key (chars)
502 {
503 var ch = '?';
504 if (flag_shiftlock || flag_shift)
505 {
506 ch = chars.substr(1,1);
507 }
508 else if (flag_ctrl)
509 {
510 ch = chars.substr(2,1);
511 }
512 else
513 {
514 ch = chars.substr(0,1);
515 }
516 load_url_to_screen('cgishell.cgi?ajax=send&sid=%(SID)s&arg=' + escape(ch));
517 if (flag_shift || flag_ctrl)
518 {
519 flag_shift = 0;
520 flag_ctrl = 0;
521 }
522 update_button_colors();
523 }
524
525 function key_shiftlock()
526 {
527 flag_ctrl = 0;
528 flag_shift = 0;
529 if (flag_shiftlock)
530 {
531 flag_shiftlock = 0;
532 }
533 else
534 {
535 flag_shiftlock = 1;
536 }
537 update_button_colors();
538 }
539
540 function key_shift()
541 {
542 if (flag_shift)
543 {
544 flag_shift = 0;
545 }
546 else
547 {
548 flag_ctrl = 0;
549 flag_shiftlock = 0;
550 flag_shift = 1;
551 }
552 update_button_colors();
553 }
554 function key_ctrl ()
555 {
556 if (flag_ctrl)
557 {
558 flag_ctrl = 0;
559 }
560 else
561 {
562 flag_ctrl = 1;
563 flag_shiftlock = 0;
564 flag_shift = 0;
565 }
566
567 update_button_colors();
568 }
569 function update_button_colors ()
570 {
571 if (flag_ctrl)
572 {
573 document.form['Ctrl'].style.backgroundColor = ButtonOnColor;
574 document.form['Ctrl2'].style.backgroundColor = ButtonOnColor;
575 }
576 else
577 {
578 document.form['Ctrl'].style.backgroundColor = document.form.style.backgr oundColor;
579 document.form['Ctrl2'].style.backgroundColor = document.form.style.backg roundColor;
580 }
581 if (flag_shift)
582 {
583 document.form['Shift'].style.backgroundColor = ButtonOnColor;
584 document.form['Shift2'].style.backgroundColor = ButtonOnColor;
585 }
586 else
587 {
588 document.form['Shift'].style.backgroundColor = document.form.style.backg roundColor;
589 document.form['Shift2'].style.backgroundColor = document.form.style.back groundColor;
590 }
591 if (flag_shiftlock)
592 {
593 document.form['ShiftLock'].style.backgroundColor = ButtonOnColor;
594 }
595 else
596 {
597 document.form['ShiftLock'].style.backgroundColor = document.form.style.b ackgroundColor;
598 }
599
600 }
601 function keyHandler(e)
602 {
603 var pressedKey;
604 if (document.all) { e = window.event; }
605 if (document.layers) { pressedKey = e.which; }
606 if (document.all) { pressedKey = e.keyCode; }
607 pressedCharacter = String.fromCharCode(pressedKey);
608 type_key(pressedCharacter+pressedCharacter+pressedCharacter);
609 alert(pressedCharacter);
610 // alert(' Character = ' + pressedCharacter + ' [Decimal value = ' + pressedK ey + ']');
611 }
612 //document.onkeypress = keyHandler;
613 //if (document.layers)
614 // document.captureEvents(Event.KEYPRESS);
615 //http://sniptools.com/jskeys
616 //document.onkeyup = KeyCheck;
617 function KeyCheck(e)
618 {
619 var KeyID = (window.event) ? event.keyCode : e.keyCode;
620 type_key(String.fromCharCode(KeyID));
621 e.cancelBubble = true;
622 window.event.cancelBubble = true;
623 }
624 </script>
625
626 </head>
627
628 <body onload="init()">
629 <form id="form" name="form" action="/cgi-bin/cgishell.cgi" method="POST">
630 <input name="sid" value="%(SID)s" type="hidden">
631 <textarea name="screen_text" cols="81" rows="25">%(SHELL_OUTPUT)s</textarea>
632 <hr noshade="1">
633 &nbsp;<input name="cli" id="cli" type="text" size="80"><br>
634 <table border="0" align="left">
635 <tr>
636 <td width="86%%" align="center">
637 <input name="submit" type="submit" value="Submit">
638 <input name="refresh" type="button" value="REFRESH" onclick="refresh_screen( )">
639 <input name="refresh" type="button" value="CURSOR" onclick="query_cursor()">
640 <input name="hash" type="button" value="HASH" onclick="query_hash()">
641 <input name="exit" type="button" value="EXIT" onclick="exit_server()">
642 <br>
643 <input type="button" value="Esc" onclick="type_key('\\x1b\\x1b')" />
644 <input type="button" value="` ~" onclick="type_key('`~')" />
645 <input type="button" value="1!" onclick="type_key('1!')" />
646 <input type="button" value="2@" onclick="type_key('2@\\x00')" />
647 <input type="button" value="3#" onclick="type_key('3#')" />
648 <input type="button" value="4$" onclick="type_key('4$')" />
649 <input type="button" value="5%%" onclick="type_key('5%%')" />
650 <input type="button" value="6^" onclick="type_key('6^\\x1E')" />
651 <input type="button" value="7&" onclick="type_key('7&')" />
652 <input type="button" value="8*" onclick="type_key('8*')" />
653 <input type="button" value="9(" onclick="type_key('9(')" />
654 <input type="button" value="0)" onclick="type_key('0)')" />
655 <input type="button" value="-_" onclick="type_key('-_\\x1F')" />
656 <input type="button" value="=+" onclick="type_key('=+')" />
657 <input type="button" value="BkSp" onclick="type_key('\\x08\\x08\\x08')" />
658 <br>
659 <input type="button" value="Tab" onclick="type_key('\\t\\t')" />
660 <input type="button" value="Q" onclick="type_key('qQ\\x11')" />
661 <input type="button" value="W" onclick="type_key('wW\\x17')" />
662 <input type="button" value="E" onclick="type_key('eE\\x05')" />
663 <input type="button" value="R" onclick="type_key('rR\\x12')" />
664 <input type="button" value="T" onclick="type_key('tT\\x14')" />
665 <input type="button" value="Y" onclick="type_key('yY\\x19')" />
666 <input type="button" value="U" onclick="type_key('uU\\x15')" />
667 <input type="button" value="I" onclick="type_key('iI\\x09')" />
668 <input type="button" value="O" onclick="type_key('oO\\x0F')" />
669 <input type="button" value="P" onclick="type_key('pP\\x10')" />
670 <input type="button" value="[ {" onclick="type_key('[{\\x1b')" />
671 <input type="button" value="] }" onclick="type_key(']}\\x1d')" />
672 <input type="button" value="\\ |" onclick="type_key('\\\\|\\x1c')" />
673 <br>
674 <input type="button" id="Ctrl" value="Ctrl" onclick="key_ctrl()" />
675 <input type="button" value="A" onclick="type_key('aA\\x01')" />
676 <input type="button" value="S" onclick="type_key('sS\\x13')" />
677 <input type="button" value="D" onclick="type_key('dD\\x04')" />
678 <input type="button" value="F" onclick="type_key('fF\\x06')" />
679 <input type="button" value="G" onclick="type_key('gG\\x07')" />
680 <input type="button" value="H" onclick="type_key('hH\\x08')" />
681 <input type="button" value="J" onclick="type_key('jJ\\x0A')" />
682 <input type="button" value="K" onclick="type_key('kK\\x0B')" />
683 <input type="button" value="L" onclick="type_key('lL\\x0C')" />
684 <input type="button" value="; :" onclick="type_key(';:')" />
685 <input type="button" id="quote" value="'" onclick="type_key('\\x27\\x22')" / >
686 <input type="button" value="Enter" onclick="type_key('\\n\\n')" />
687 <br>
688 <input type="button" id="ShiftLock" value="Caps Lock" onclick="key_shiftlock ()" />
689 <input type="button" id="Shift" value="Shift" onclick="key_shift()" />
690 <input type="button" value="Z" onclick="type_key('zZ\\x1A')" />
691 <input type="button" value="X" onclick="type_key('xX\\x18')" />
692 <input type="button" value="C" onclick="type_key('cC\\x03')" />
693 <input type="button" value="V" onclick="type_key('vV\\x16')" />
694 <input type="button" value="B" onclick="type_key('bB\\x02')" />
695 <input type="button" value="N" onclick="type_key('nN\\x0E')" />
696 <input type="button" value="M" onclick="type_key('mM\\x0D')" />
697 <input type="button" value=", <" onclick="type_key(',<')" />
698 <input type="button" value=". >" onclick="type_key('.>')" />
699 <input type="button" value="/ ?" onclick="type_key('/?')" />
700 <input type="button" id="Shift2" value="Shift" onclick="key_shift()" />
701 <input type="button" id="Ctrl2" value="Ctrl" onclick="key_ctrl()" />
702 <br>
703 <input type="button" value=" FINAL FRONTIER " onclick="type_ke y(' ')" />
704 </td>
705 </tr>
706 </table>
707 </form>
708 </body>
709 </html>
710 """
711
712 LOGIN_HTML="""<html>
713 <head>
714 <title>Shell Login</title>
715 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
716 <style type=text/css>
717 a {color: #9f9; text-decoration: none}
718 a:hover {color: #0f0}
719 hr {color: #0f0}
720 html,body,textarea,input,form
721 {
722 font-family: "Courier New", Courier, mono;
723 font-size: 8pt;
724 color: #0c0;
725 background-color: #020;
726 margin:3;
727 padding:0;
728 border:0;
729 }
730 input { background-color: #010; }
731 input,textarea {
732 border-width:1;
733 border-style:solid;
734 border-color:#0c0;
735 padding:3;
736 margin:3;
737 }
738 </style>
739 <script language="JavaScript">
740 function init ()
741 {
742 document.login_form["username"].focus();
743 }
744 </script>
745 </head>
746 <body onload="init()">
747 <form name="login_form" method="POST">
748 <input name="start_server" value="1" type="hidden">
749 <input name="sid" value="%(SID)s" type="hidden">
750 username: <input name="username" type="text" size="30"><br>
751 password: <input name="password" type="password" size="30"><br>
752 <input name="submit" type="submit" value="enter">
753 </form>
754 <br>
755 </body>
756 </html>
757 """
758
759 if __name__ == "__main__":
760 try:
761 main()
762 except Exception as e:
763 print(str(e))
764 tb_dump = traceback.format_exc()
765 print(str(tb_dump))
766
OLDNEW
« no previous file with comments | « third_party/pexpect/examples/astat.py ('k') | third_party/pexpect/examples/chess.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698