1import getopt 2import os 3import sys 4import re 5 6class ArgumentError(Exception): 7 """ Exception class for raising errors in command arguments. The lldb_command framework will catch this 8 class of exceptions and print suitable error message to user. 9 """ 10 def __init__(self, msg): 11 self.error_message = msg 12 def __str__(self): 13 return str(self.error_message) 14 15 16class RedirectStdStreams(object): 17 def __init__(self, stdout=None, stderr=None): 18 self._stdout = stdout or sys.stdout 19 self._stderr = stderr or sys.stderr 20 21 def __enter__(self): 22 self.old_stdout, self.old_stderr = sys.stdout, sys.stderr 23 self.old_stdout.flush(); self.old_stderr.flush() 24 sys.stdout, sys.stderr = self._stdout, self._stderr 25 26 def __exit__(self, exc_type, exc_value, traceback): 27 self._stdout.flush(); self._stderr.flush() 28 sys.stdout = self.old_stdout 29 sys.stderr = self.old_stderr 30 31class CommandOutput(object): 32 """ 33 An output handler for all commands. Use Output.print to direct all output of macro via the handler. 34 These arguments are passed after a "--". eg 35 (lldb) zprint -- -o /tmp/zprint.out.txt 36 37 Currently this provide capabilities 38 -o path/to/filename 39 The output of this command execution will be saved to file. Parser information or errors will 40 not be sent to file though. eg /tmp/output.txt 41 -s filter_string 42 the "filter_string" param is parsed to python regex expression and each line of output 43 will be printed/saved only if it matches the expression. 44 The command header will not be filtered in any case. 45 """ 46 def __init__(self, CommandResult): 47 """ Create a new instance to handle command output. 48 params: 49 CommandResult : SBCommandReturnObject result param from lldb's command invocation. 50 """ 51 self.fname=None 52 self.fhandle=None 53 self.FILTER=False 54 self.pluginRequired = False 55 self.pluginName = None 56 self.resultObj = CommandResult 57 self.immediateOutput = False 58 self.verbose_level = 0 59 self.target_cmd_args = [] 60 self.target_cmd_options = {} 61 62 def write(self, s): 63 """ Handler for all commands output. By default just print to stdout """ 64 if self.FILTER and not self.reg.search(s): return 65 if self.FILTER : s+="\n" 66 if self.fhandle != None: self.fhandle.write(s) 67 else: 68 if self.immediateOutput: 69 sys.__stdout__.write(s) 70 else: 71 res_str = s 72 if s.endswith("\n"): 73 res_str = s[:-1] 74 if self.resultObj and len(res_str) > 0: self.resultObj.AppendMessage(res_str) 75 76 def flush(self): 77 if self.fhandle != None: 78 self.fhandle.flush() 79 80 def __del__(self): 81 """ closes any open files. report on any errors """ 82 if self.fhandle != None : 83 self.fhandle.close() 84 85 def setOptions(self,cmdargs, cmdoptions =''): 86 """ parse the arguments passed to the command 87 param : 88 cmdargs => [] of <str> (typically args.split()) 89 cmdoptions : str - string of command level options. 90 These should be CAPITAL LETTER options only. 91 """ 92 opts=() 93 args = cmdargs 94 cmdoptions = cmdoptions.upper() 95 try: 96 opts,args = getopt.gnu_getopt(args,'hvo:s:p:'+ cmdoptions,[]) 97 self.target_cmd_args = args 98 except getopt.GetoptError,err: 99 raise ArgumentError(str(err)) 100 #continue with processing 101 for o,a in opts : 102 if o == "-h": 103 # This is misuse of exception but 'self' has no info on doc string. 104 # The caller may handle exception and display appropriate info 105 raise ArgumentError("HELP") 106 if o == "-o" and len(a) > 0: 107 self.fname=os.path.normpath(os.path.expanduser(a.strip())) 108 self.fhandle=open(self.fname,"w") 109 print "saving results in file ",str(a) 110 self.fhandle.write("(lldb)%s \n" % " ".join(cmdargs)) 111 elif o == "-s" and len(a) > 0: 112 self.reg = re.compile(a.strip(),re.MULTILINE|re.DOTALL) 113 self.FILTER=True 114 print "showing results for regex:",a.strip() 115 elif o == "-p" and len(a) > 0: 116 self.pluginRequired = True 117 self.pluginName = a.strip() 118 #print "passing output to " + a.strip() 119 elif o == "-v" : 120 self.verbose_level += 1 121 else: 122 o = o.strip() 123 self.target_cmd_options[o] = a 124 125 126 127 128