def test_circular_list(): def f(): l = [None] l[0] = l return l lst = psyco.proxy(f)() assert type(lst) is list assert len(lst) == 1 assert lst[0] is lst def g(): a = [None] b = [None] a[0] = b b[0] = a return b lst = psyco.proxy(g)() assert type(lst) is list assert len(lst) == 1 assert lst[0] is not lst assert type(lst[0]) is list assert len(lst[0]) == 1 assert lst[0][0] is lst
def test_math_module(): import math global _operation for name in ["acos", "asin", "atan", "ceil", "cos", "cosh", "exp", "fabs", "floor", "sin", "sinh", "sqrt", "tan", "tanh"]: _operation = getattr(math, name) def tester(a): return _operation(a) res = psyco.proxy(tester)(0.17) assert abs(res - _operation(0.17)) < 1e6 def tester(a): return _operation(*a) res = psyco.proxy(tester)((0.71,)) assert abs(res - _operation(0.71)) < 1e6 for name in ["atan2", "fmod", "hypot", "pow"]: _operation = getattr(math, name) def tester(a, b): return _operation(a, b) res = psyco.proxy(tester)(0.17, 0.081) assert abs(res - _operation(0.17, 0.081)) < 1e6 def tester(a): return _operation(*a) res = psyco.proxy(tester)((0.71, 0.2643)) assert abs(res - _operation(0.71, 0.2643)) < 1e6
def test_math_module(): import math global _operation for name in [ "acos", "asin", "atan", "ceil", "cos", "cosh", "exp", "fabs", "floor", "sin", "sinh", "sqrt", "tan", "tanh" ]: _operation = getattr(math, name) def tester(a): return _operation(a) res = psyco.proxy(tester)(0.17) assert abs(res - _operation(0.17)) < 1e6 def tester(a): return _operation(*a) res = psyco.proxy(tester)((0.71, )) assert abs(res - _operation(0.71)) < 1e6 for name in ["atan2", "fmod", "hypot", "pow"]: _operation = getattr(math, name) def tester(a, b): return _operation(a, b) res = psyco.proxy(tester)(0.17, 0.081) assert abs(res - _operation(0.17, 0.081)) < 1e6 def tester(a): return _operation(*a) res = psyco.proxy(tester)((0.71, 0.2643)) assert abs(res - _operation(0.71, 0.2643)) < 1e6
def proxy_defargs(): d = {} exec """ def f(): g() def g(a=12): print a """ in d d['f'] = psyco.proxy(d['f']) d['g'] = psyco.proxy(d['g']) d['f']()
def test_init_arguments(): import py def f1(): Rect() def f2(): psyco.compact(12) def f3(): ClassWithNoInit(21) py.test.raises(TypeError, f1) if sys.version >= (2, 3): py.test.raises(TypeError, f2) py.test.raises(TypeError, f3) py.test.raises(TypeError, psyco.proxy(f1)) if sys.version >= (2, 3): py.test.raises(TypeError, psyco.proxy(f2)) py.test.raises(TypeError, psyco.proxy(f3))
def setfilter(): def f1(): return ('f1', int(__in_psyco__)) def f2(): "TAGGY" return ('f2', int(__in_psyco__)) def myfilter(co): return co.co_consts[0] != 'TAGGY' psyco.setfilter(myfilter) try: print psyco.proxy(f1)() # ('f1', 1) print psyco.proxy(f2)() # ('f2', 0) finally: prev = psyco.setfilter(None) assert prev is myfilter
def test_nonfloat_in_math(): class X(object): def __float__(self): return -123.45 def f(x): return math.ceil(x), math.floor(x) assert psyco.proxy(f)(X()) == (-123.0, -124.0)
def test_id(): def f(x): return id(x) obj = [] res = psyco.proxy(f)(obj) assert res == id(obj)
def test_big_dict_constructor(): def f(x): return { 1: 2, 3: 4, x: 6, 7: 8, 9: x, 'a': 'a', 'b': 'c', 'd': 'e', 'f': 'g' } assert psyco.proxy(f)(5) == f(5) assert psyco.proxy(f)('b') == f('b')
def gridloop_psyco_init(self, method): """Try to accelerate Grid2D.gridloop with psyco.""" # define method self.gridloop_psyco: try: import psyco self.gridloop_psyco = psyco.proxy(method) except ImportError: self.gridloop_psyco = method
def pystones_psycho(*loopslist): import psyco #old_dict = Record.__dict__.copy() #try: # replace all methods of Record by proxies #for key, value in old_dict.items(): # if type(value) is type(main): # Record.__dict__[key] = _psyco.proxy(value, 99) f = psyco.proxy(Proc0) return map(f, loopslist)
def optimize(func): """ A decorator to wrap a function or method in a ``psyco.proxy`` call to optimize it, falling back to the original function if psyco is not available. """ if psyco is None: return func return functools.update_wrapper(psyco.proxy(func), func)
def test_slice_overflow(): class X(object): def __len__(self): return sys.maxint def __getslice__(self, i, j): return i, j def f(X): return X()[-(2**100):2**100] res = psyco.proxy(f)(X) assert res == f(X)
def test_index(): if sys.version_info < (2, 5): py.test.skip("for Python 2.5") class X(object): def __index__(self): return -3 def f(x): return (12, 23, 34, 45)[x] res = psyco.proxy(f)(X()) assert res == 23
def test_index_repeat(): if sys.version_info < (2, 5): py.test.skip("for Python 2.5") class X(object): def __index__(self): return 3 def f(x): return (12, 23) * x res = psyco.proxy(f)(X()) assert res == (12, 23, 12, 23, 12, 23)
def timed(func, *args, **kw): """times a function with and without using psyco""" start = time() func(*args,**kw) end = time() withoutpsyco = end-start print "Took",withoutpsyco,"without psyco" start = time() accfunc = psyco.proxy(func) accfunc(*args,**kw) end = time() withpsyco = end-start print "Took",withpsyco,"with psyco" print "A",withoutpsyco/withpsyco,"x speedup"
def go(f, *args): print '-' * 80 v1, t1 = time(psyco.proxy(f), *args) print v1 print '^^^ computed by Psyco in %s seconds' % t1 v2, t2 = time(f, *args) if v1 == v2: if t1 and t2: s = ', Psyco is %.2f times faster' % (t2 / float(t1)) else: s = '' print 'Python got the same result in %s seconds%s' % (t2, s) else: print v2 print '^^^ by Python in %s seconds' % t2 print '*' * 80 print '!!! different results !!!'
def go(f, *args): print '-' * 78 v1, t1 = time(psyco.proxy(f), *args) print v1 print '^^^ computed by Psyco in %s seconds' % t1 v2, t2 = time(f, *args) if v1 == v2: if t1 and t2: ok = '%.2f times faster' % (t2 / float(t1)) s = ', Psyco is %s' % ok else: ok = s = '' print 'Python got the same result in %s seconds%s' % (t2, s) else: print v2 print '^^^ by Python in %s seconds' % t2 print '*' * 78 print '!!! different results !!!' ok = 'DIFFERENT RESULTS' ALLTESTS.append((f.func_name, t2, t1, ok))
def go(f, *args): print '-'*78 v1, t1 = time(psyco.proxy(f), *args) print v1 print '^^^ computed by Psyco in %s seconds' % t1 v2, t2 = time(f, *args) if v1 == v2: if t1 and t2: ok = '%.2f times faster' % (t2/float(t1)) s = ', Psyco is %s' % ok else: ok = s = '' print 'Python got the same result in %s seconds%s' % (t2, s) else: print v2 print '^^^ by Python in %s seconds' % t2 print '*'*78 print '!!! different results !!!' ok = 'DIFFERENT RESULTS' ALLTESTS.append((f.func_name,t2,t1,ok))
def test_index_slice(): if sys.version_info < (2, 5): py.test.skip("for Python 2.5") class Observer(object): def __getslice__(self, i, j): return "slice", i, j def __getitem__(self, x): raise Exception("in __getitem__") class X(object): def __index__(self): return 5 class Y(object): def __index__(self): return -2 def f(o, x, y): return o[x:y] res = psyco.proxy(f)(Observer(), X(), Y()) assert res == ("slice", 5, -2)
u'Замена атрибутов дочернего объекта [%s] ресурса <%s>' % (attr_name, ResName_)) else: io_prnt.outWarning( u'Не поддерживаемый тип %s замены ресурса дочернего объекта <%s>' % (type(value), attr_name)) if not context: context = icwidget.icResObjContext() return icBuildObject(parent, res, evalSpace=context, id=kwargs.get('id', None)) return None except: io_prnt.outErr('CREATE OBJECT ERROR: [%s . %s]' % (ResName_, ResExt_)) return None # Компилируем функцию разбора ресурсного описания, тут # могут быть большие накладные расходы на интерпретацию try: import psyco icResourceParser = psyco.proxy(icResourceParser) except: pass if __name__ == '__main__': pass
class PyDBFrame: '''This makes the tracing for a given frame, so, the trace_dispatch is used initially when we enter into a new context ('call') and then is reused for the entire context. ''' #Note: class (and not instance) attributes. #Same thing in the main debugger but only considering the file contents, while the one in the main debugger #considers the user input (so, the actual result must be a join of both). filename_to_lines_where_exceptions_are_ignored = {} filename_to_stat_info = {} def __init__(self, args): #args = mainDebugger, filename, base, info, t, frame #yeap, much faster than putting in self and then getting it from self later on self._args = args[:-1] def setSuspend(self, *args, **kwargs): self._args[0].setSuspend(*args, **kwargs) def doWaitSuspend(self, *args, **kwargs): self._args[0].doWaitSuspend(*args, **kwargs) def trace_exception(self, frame, event, arg): if event == 'exception': flag, frame = self.should_stop_on_exception(frame, event, arg) if flag: self.handle_exception(frame, event, arg) return self.trace_dispatch return self.trace_exception def should_stop_on_exception(self, frame, event, arg): mainDebugger, _filename, info, thread = self._args flag = False if info.pydev_state != STATE_SUSPEND: #and breakpoint is not None: exception, value, trace = arg if trace is not None: #on jython trace is None on the first event exception_breakpoint = get_exception_breakpoint( exception, mainDebugger.break_on_caught_exceptions) if exception_breakpoint is not None: if not exception_breakpoint.notify_on_first_raise_only or just_raised( trace): # print frame.f_code.co_name add_exception_to_frame(frame, (exception, value, trace)) thread.additionalInfo.message = exception_breakpoint.qname flag = True else: flag = False else: try: result = mainDebugger.plugin.exception_break( mainDebugger, self, frame, self._args, arg) if result: (flag, frame) = result except: flag = False return flag, frame def handle_exception(self, frame, event, arg): try: # print 'handle_exception', frame.f_lineno, frame.f_code.co_name # We have 3 things in arg: exception type, description, traceback object trace_obj = arg[2] mainDebugger = self._args[0] if not hasattr(trace_obj, 'tb_next'): return #Not always there on Jython... initial_trace_obj = trace_obj if trace_obj.tb_next is None and trace_obj.tb_frame is frame: #I.e.: tb_next should be only None in the context it was thrown (trace_obj.tb_frame is frame is just a double check). if mainDebugger.break_on_exceptions_thrown_in_same_context: #Option: Don't break if an exception is caught in the same function from which it is thrown return else: #Get the trace_obj from where the exception was raised... while trace_obj.tb_next is not None: trace_obj = trace_obj.tb_next if mainDebugger.ignore_exceptions_thrown_in_lines_with_ignore_exception: for check_trace_obj in (initial_trace_obj, trace_obj): filename = GetFilenameAndBase(check_trace_obj.tb_frame)[0] filename_to_lines_where_exceptions_are_ignored = self.filename_to_lines_where_exceptions_are_ignored lines_ignored = filename_to_lines_where_exceptions_are_ignored.get( filename) if lines_ignored is None: lines_ignored = filename_to_lines_where_exceptions_are_ignored[ filename] = {} try: curr_stat = os.stat(filename) curr_stat = (curr_stat.st_size, curr_stat.st_mtime) except: curr_stat = None last_stat = self.filename_to_stat_info.get(filename) if last_stat != curr_stat: self.filename_to_stat_info[filename] = curr_stat lines_ignored.clear() try: linecache.checkcache(filename) except: #Jython 2.1 linecache.checkcache() from_user_input = mainDebugger.filename_to_lines_where_exceptions_are_ignored.get( filename) if from_user_input: merged = {} merged.update(lines_ignored) #Override what we have with the related entries that the user entered merged.update(from_user_input) else: merged = lines_ignored exc_lineno = check_trace_obj.tb_lineno # print ('lines ignored', lines_ignored) # print ('user input', from_user_input) # print ('merged', merged, 'curr', exc_lineno) if not DictContains( merged, exc_lineno ): #Note: check on merged but update lines_ignored. try: line = linecache.getline( filename, exc_lineno, check_trace_obj.tb_frame.f_globals) except: #Jython 2.1 line = linecache.getline(filename, exc_lineno) if IGNORE_EXCEPTION_TAG.match(line) is not None: lines_ignored[exc_lineno] = 1 return else: #Put in the cache saying not to ignore lines_ignored[exc_lineno] = 0 else: #Ok, dict has it already cached, so, let's check it... if merged.get(exc_lineno, 0): return thread = self._args[3] try: frame_id_to_frame = {} frame_id_to_frame[id(frame)] = frame f = trace_obj.tb_frame while f is not None: frame_id_to_frame[id(f)] = f f = f.f_back f = None thread_id = GetThreadId(thread) pydevd_vars.addAdditionalFrameById(thread_id, frame_id_to_frame) try: mainDebugger.sendCaughtExceptionStack( thread, arg, id(frame)) self.setSuspend(thread, CMD_STEP_CAUGHT_EXCEPTION) self.doWaitSuspend(thread, frame, event, arg) mainDebugger.sendCaughtExceptionStackProceeded(thread) finally: pydevd_vars.removeAdditionalFrameById(thread_id) except: traceback.print_exc() mainDebugger.SetTraceForFrameAndParents(frame) finally: #Clear some local variables... trace_obj = None initial_trace_obj = None check_trace_obj = None f = None frame_id_to_frame = None mainDebugger = None thread = None def trace_dispatch(self, frame, event, arg): main_debugger, filename, info, thread = self._args try: info.is_tracing = True if main_debugger._finishDebuggingSession: return None if getattr(thread, 'pydev_do_not_trace', None): return None if event == 'call' and main_debugger.signature_factory: sendSignatureCallTrace(main_debugger, frame, filename) plugin_manager = main_debugger.plugin is_exception_event = event == 'exception' has_exception_breakpoints = main_debugger.break_on_caught_exceptions \ or plugin_manager.has_exception_breaks(main_debugger) if is_exception_event: if has_exception_breakpoints: flag, frame = self.should_stop_on_exception( frame, event, arg) if flag: self.handle_exception(frame, event, arg) return self.trace_dispatch elif event not in ('line', 'call', 'return'): #I believe this can only happen in jython on some frontiers on jython and java code, which we don't want to trace. return None stop_frame = info.pydev_step_stop step_cmd = info.pydev_step_cmd if is_exception_event: breakpoints_for_file = None else: # If we are in single step mode and something causes us to exit the current frame, we need to make sure we break # eventually. Force the step mode to step into and the step stop frame to None. # I.e.: F6 in the end of a function should stop in the next possible position (instead of forcing the user # to make a step in or step over at that location). # Note: this is especially troublesome when we're skipping code with the # @DontTrace comment. if stop_frame is frame and event in ( 'return', 'exception') and step_cmd in (CMD_STEP_RETURN, CMD_STEP_OVER): info.pydev_step_cmd = CMD_STEP_INTO info.pydev_step_stop = None breakpoints_for_file = main_debugger.breakpoints.get(filename) can_skip = False if info.pydev_state == STATE_RUN: #we can skip if: #- we have no stop marked #- we should make a step return/step over and we're not in the current frame can_skip = (step_cmd is None and stop_frame is None)\ or (step_cmd in (CMD_STEP_RETURN, CMD_STEP_OVER) and stop_frame is not frame) if can_skip: can_skip = not plugin_manager.can_not_skip( main_debugger, self, frame) # Let's check to see if we are in a function that has a breakpoint. If we don't have a breakpoint, # we will return nothing for the next trace #also, after we hit a breakpoint and go to some other debugging state, we have to force the set trace anyway, #so, that's why the additional checks are there. if not breakpoints_for_file: if can_skip: if has_exception_breakpoints: return self.trace_exception else: return None else: #checks the breakpoint to see if there is a context match in some function curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' for breakpoint in DictIterValues( breakpoints_for_file ): #jython does not support itervalues() #will match either global or some function if breakpoint.func_name in ('None', curr_func_name): break else: # if we had some break, it won't get here (so, that's a context that we want to skip) if can_skip: if has_exception_breakpoints: return self.trace_exception else: return None #We may have hit a breakpoint or we are already in step mode. Either way, let's check what we should do in this frame #print 'NOT skipped', frame.f_lineno, frame.f_code.co_name, event try: line = frame.f_lineno flag = False #return is not taken into account for breakpoint hit because we'd have a double-hit in this case #(one for the line and the other for the return). stop_info = {} breakpoint = None exist_result = False stop_info['stop'] = False if not flag and event != 'return' and info.pydev_state != STATE_SUSPEND and breakpoints_for_file is not None \ and DictContains(breakpoints_for_file, line): breakpoint = breakpoints_for_file[line] new_frame = frame stop_info['stop'] = True if step_cmd == CMD_STEP_OVER and stop_frame is frame and event in ( 'line', 'return'): stop_info[ 'stop'] = False #we don't stop on breakpoint if we have to stop by step-over (it will be processed later) else: result = plugin_manager.get_breakpoint( main_debugger, self, frame, event, self._args) if result: exist_result = True (flag, breakpoint, new_frame) = result if breakpoint: #ok, hit breakpoint, now, we have to discover if it is a conditional breakpoint # lets do the conditional stuff here if stop_info['stop'] or exist_result: condition = breakpoint.condition if condition is not None: try: val = eval(condition, new_frame.f_globals, new_frame.f_locals) if not val: return self.trace_dispatch except: if type(condition) != type(''): if hasattr(condition, 'encode'): condition = condition.encode('utf-8') msg = 'Error while evaluating expression: %s\n' % ( condition, ) sys.stderr.write(msg) traceback.print_exc() if not main_debugger.suspend_on_breakpoint_exception: return self.trace_dispatch else: stop_info['stop'] = True try: additional_info = None try: additional_info = thread.additionalInfo except AttributeError: pass #that's ok, no info currently set if additional_info is not None: # add exception_type and stacktrace into thread additional info etype, value, tb = sys.exc_info() try: error = ''.join( traceback. format_exception_only( etype, value)) stack = traceback.extract_stack( f=tb.tb_frame.f_back) # On self.setSuspend(thread, CMD_SET_BREAK) this info will be # sent to the client. additional_info.conditional_breakpoint_exception = \ ('Condition:\n' + condition + '\n\nError:\n' + error, stack) finally: etype, value, tb = None, None, None except: traceback.print_exc() if breakpoint.expression is not None: try: try: val = eval(breakpoint.expression, new_frame.f_globals, new_frame.f_locals) except: val = sys.exc_info()[1] finally: if val is not None: thread.additionalInfo.message = val if stop_info['stop']: self.setSuspend(thread, CMD_SET_BREAK) elif flag: result = plugin_manager.suspend(main_debugger, thread, frame) if result: frame = result # if thread has a suspend flag, we suspend with a busy wait if info.pydev_state == STATE_SUSPEND: self.doWaitSuspend(thread, frame, event, arg) return self.trace_dispatch except: traceback.print_exc() raise #step handling. We stop when we hit the right frame try: should_skip = False if pydevd_dont_trace.should_trace_hook is not None: if not hasattr(self, 'should_skip'): # I.e.: cache the result on self.should_skip (no need to evaluate the same frame multiple times). # Note that on a code reload, we won't re-evaluate this because in practice, the frame.f_code # Which will be handled by this frame is read-only, so, we can cache it safely. should_skip = self.should_skip = not pydevd_dont_trace.should_trace_hook( frame, filename) else: should_skip = self.should_skip if should_skip: stop_info['stop'] = False elif step_cmd == CMD_STEP_INTO: stop_info['stop'] = event in ('line', 'return') plugin_manager.cmd_step_into(main_debugger, frame, event, self._args, stop_info) elif step_cmd == CMD_STEP_OVER: stop_info['stop'] = stop_frame is frame and event in ( 'line', 'return') plugin_manager.cmd_step_over(main_debugger, frame, event, self._args, stop_info) elif step_cmd == CMD_SMART_STEP_INTO: stop_info['stop'] = False if info.pydev_smart_step_stop is frame: info.pydev_func_name = None info.pydev_smart_step_stop = None if event == 'line' or event == 'exception': curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ( '?', '<module>') or curr_func_name is None: curr_func_name = '' if curr_func_name == info.pydev_func_name: stop_info['stop'] = True elif step_cmd == CMD_STEP_RETURN: stop_info[ 'stop'] = event == 'return' and stop_frame is frame elif step_cmd == CMD_RUN_TO_LINE or step_cmd == CMD_SET_NEXT_STATEMENT: stop_info['stop'] = False if event == 'line' or event == 'exception': #Yes, we can only act on line events (weird hum?) #Note: This code is duplicated at pydevd.py #Acting on exception events after debugger breaks with exception curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' if curr_func_name == info.pydev_func_name: line = info.pydev_next_line if frame.f_lineno == line: stop_info['stop'] = True else: if frame.f_trace is None: frame.f_trace = self.trace_dispatch frame.f_lineno = line frame.f_trace = None stop_info['stop'] = True else: stop_info['stop'] = False if True in DictIterValues(stop_info): stopped_on_plugin = plugin_manager.stop( main_debugger, frame, event, self._args, stop_info, arg, step_cmd) if DictContains( stop_info, 'stop' ) and stop_info['stop'] and not stopped_on_plugin: if event == 'line': self.setSuspend(thread, step_cmd) self.doWaitSuspend(thread, frame, event, arg) else: #return event back = frame.f_back if back is not None: #When we get to the pydevd run function, the debugging has actually finished for the main thread #(note that it can still go on for other threads, but for this one, we just make it finish) #So, just setting it to None should be OK base = basename(back.f_code.co_filename) if base == 'pydevd.py' and back.f_code.co_name == 'run': back = None elif base == 'pydevd_traceproperty.py': # We dont want to trace the return event of pydevd_traceproperty (custom property for debugging) #if we're in a return, we want it to appear to the user in the previous frame! return None if back is not None: #if we're in a return, we want it to appear to the user in the previous frame! self.setSuspend(thread, step_cmd) self.doWaitSuspend(thread, back, event, arg) else: #in jython we may not have a back frame info.pydev_step_stop = None info.pydev_step_cmd = None info.pydev_state = STATE_RUN except: try: traceback.print_exc() info.pydev_step_cmd = None except: return None #if we are quitting, let's stop the tracing retVal = None if not main_debugger.quitting: retVal = self.trace_dispatch return retVal finally: info.is_tracing = False #end trace_dispatch if USE_PSYCO_OPTIMIZATION: try: import psyco trace_dispatch = psyco.proxy(trace_dispatch) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear() #don't keep the traceback pass #ok, psyco not available
class ChaCha(object): """ ChaCha is an improved variant of Salsa20. Salsa20 was submitted to eSTREAM, an EU stream cipher competition. Salsa20 was originally defined to be 20 rounds. Reduced round versions, Salsa20/8 (8 rounds) and Salsa20/12 (12 rounds), were later submitted. Salsa20/12 was chosen as one of the winners and 12 rounds was deemed the "right blend" of security and efficiency. Salsa20 is about 3x-4x faster than AES-128. Both ChaCha and Salsa20 accept a 128-bit or a 256-bit key and a 64-bit IV to set up an initial 64-byte state. For each 64-bytes of data, the state gets scrambled and XORed with the previous state. This new state is then XORed with the input data to produce the output. Both being stream ciphers, their encryption and decryption functions are identical. While Salsa20's diffusion properties are very good, some claimed the IV/keystream correlation was too strong for comfort. To satisfy, another variant called XSalsa20 implements a 128-bit IV. For the record, EU eSTREAM team did select Salsa20/12 as a solid cipher providing 128-bit security. ChaCha is a minor tweak of Salsa20 that significantly improves its diffusion per round. ChaCha is more secure than Salsa20 and 8 rounds of ChaCha, aka ChaCha8, provides 128-bit security. (FWIW, I have not seen any calls for a 128-bit IV version of ChaCha or XChaCha.) Another benefit is that ChaCha8 is about 5-8% faster than Salsa20/8 on most 32- and 64-bit PPC and Intel processors. SIMD machines should see even more improvement. Sample usage: from chacha import ChaCha cc8 = ChaCha(key, iv) ciphertext = cc8.encrypt(plaintext) cc8 = ChaCha(key, iv) plaintext = cc8.decrypt(ciphertext) Remember, the purpose of this program is educational; it is NOT a secure implementation nor is a pure Python version going to be fast. Encrypting large data will be less than satisfying. Also, no effort is made to protect the key or wipe critical memory after use. Note that psyco, a specializing compiler somewhat akin to a JIT, can provide a 2x+ performance improvement over vanilla Python 32-bit architectures. A 64-bit version of psyco does not exist. See http://psyco.sourceforge.net For more information about Daniel Bernstein's ChaCha algorithm, please see http://cr.yp.to/chacha.html All we need now is a keystream AND authentication in the same pass. Larry Bugbee May 2009 (Salsa20) August 2009 (ChaCha) rev June 2010 """ TAU = (0x61707865, 0x3120646e, 0x79622d36, 0x6b206574) SIGMA = (0x61707865, 0x3320646e, 0x79622d32, 0x6b206574) ROUNDS = 8 # ...10, 12, 20? # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def __init__(self, key, iv, rounds=ROUNDS): """ Both key and iv are byte strings. The key must be exactly 16 or 32 bytes, 128 or 256 bits respectively. The iv must be exactly 8 bytes (64 bits) and MUST never be reused with the same key. The default number of rounds is 8. If you have several encryptions/decryptions that use the same key, you may reuse the same instance and simply call iv_setup() to set the new iv. The previous key and the new iv will establish a new state. """ self._key_setup(key) self.iv_setup(iv) self.rounds = rounds # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def _key_setup(self, key): """ key is converted to a list of 4-byte unsigned integers (32 bits). Calling this routine with a key value effectively resets the context/instance. Be sure to set the iv as well. """ if len(key) not in [16, 32]: raise Exception('key must be either 16 or 32 bytes') key_state = [0] * 16 if len(key) == 16: k = list(struct.unpack('<4I', key)) key_state[0] = self.TAU[0] key_state[1] = self.TAU[1] key_state[2] = self.TAU[2] key_state[3] = self.TAU[3] key_state[4] = k[0] key_state[5] = k[1] key_state[6] = k[2] key_state[7] = k[3] key_state[8] = k[0] key_state[9] = k[1] key_state[10] = k[2] key_state[11] = k[3] # 12 and 13 are reserved for the counter # 14 and 15 are reserved for the IV elif len(key) == 32: k = list(struct.unpack('<8I', key)) key_state[0] = self.SIGMA[0] key_state[1] = self.SIGMA[1] key_state[2] = self.SIGMA[2] key_state[3] = self.SIGMA[3] key_state[4] = k[0] key_state[5] = k[1] key_state[6] = k[2] key_state[7] = k[3] key_state[8] = k[4] key_state[9] = k[5] key_state[10] = k[6] key_state[11] = k[7] # 12 and 13 are reserved for the counter # 14 and 15 are reserved for the IV self.key_state = key_state # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def iv_setup(self, iv): """ self.state and other working structures are lists of 4-byte unsigned integers (32 bits). The iv is not a secret but it should never be reused with the same key value. Use date, time or some other counter to be sure the iv is different each time, and be sure to communicate the IV to the receiving party. Prepending 8 bytes of iv to the ciphertext is the usual way to do this. Just as setting a new key value effectively resets the context, setting the iv also resets the context with the last key value entered. """ if len(iv) != 8: raise Exception('iv must be 8 bytes') v = list(struct.unpack('<2I', iv)) iv_state = self.key_state[:] iv_state[12] = 0 iv_state[13] = 0 iv_state[14] = v[0] iv_state[15] = v[1] self.state = iv_state self.lastblock_sz = 64 # init flag - unsafe to continue # processing if not 64 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def encrypt(self, datain): """ Encrypt a chunk of data. datain and the returned value are byte strings. If large data is submitted to this routine in chunks, the chunk size MUST be an exact multiple of 64 bytes. Only the final chunk may be less than an even multiple. (This function does not "save" any uneven, left-over data for concatenation to the front of the next chunk.) The amount of available memory imposes a poorly defined limit on the amount of data this routine can process. Typically 10's and 100's of KB are available but then, perhaps not. This routine is intended for educational purposes so application developers should take heed. """ if self.lastblock_sz != 64: raise Exception('last chunk size not a multiple of 64 bytes') dataout = [] while datain: # generate 64 bytes of cipher stream stream = self._chacha_scramble() # XOR the stream onto the next 64 bytes of data dataout.append(self._xor(stream, datain)) if len(datain) <= 64: self.lastblock_sz = len(datain) return ''.join(dataout) # increment the iv. In this case we increment words # 12 and 13 in little endian order. This will work # nicely for data up to 2^70 bytes (1,099,511,627,776GB) # in length. After that it is the user's responsibility # to generate a new nonce/iv. self.state[12] = (self.state[12] + 1) & 0xffffffff if self.state[12] == 0: # if overflow in state[12] self.state[13] += 1 # carry to state[13] # not to exceed 2^70 x 2^64 = 2^134 data size ??? <<<< # get ready for the next iteration datain = datain[64:] # should never get here raise Exception('Huh?') decrypt = encrypt # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def _chacha_scramble(self): # 64 bytes in """ self.state and other working strucures are lists of 4-byte unsigned integers (32 bits). output must be converted to bytestring before return. """ x = self.state[:] # makes a copy for i in range(0, self.rounds, 2): # two rounds per iteration self._quarterround(x, 0, 4, 8, 12) self._quarterround(x, 1, 5, 9, 13) self._quarterround(x, 2, 6, 10, 14) self._quarterround(x, 3, 7, 11, 15) self._quarterround(x, 0, 5, 10, 15) self._quarterround(x, 1, 6, 11, 12) self._quarterround(x, 2, 7, 8, 13) self._quarterround(x, 3, 4, 9, 14) for i in range(16): x[i] = (x[i] + self.state[i]) & 0xffffffff output = struct.pack('<16I', x[0], x[1], x[2], x[3], x[4], x[5], x[6], x[7], x[8], x[9], x[10], x[11], x[12], x[13], x[14], x[15]) return output # 64 bytes out # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ''' # as per definition - deprecated def _quarterround(self, x, a, b, c, d): x[a] = (x[a] + x[b]) & 0xFFFFFFFF x[d] = self._rotate((x[d]^x[a]), 16) x[c] = (x[c] + x[d]) & 0xFFFFFFFF x[b] = self._rotate((x[b]^x[c]), 12) x[a] = (x[a] + x[b]) & 0xFFFFFFFF x[d] = self._rotate((x[d]^x[a]), 8) x[c] = (x[c] + x[d]) & 0xFFFFFFFF x[b] = self._rotate((x[b]^x[c]), 7) def _rotate(self, v, n): # aka ROTL32 return ((v << n) & 0xFFFFFFFF) | (v >> (32 - n)) ''' # surprisingly, the following tweaks/accelerations provide # about a 20-40% gain def _quarterround(self, x, a, b, c, d): xa = x[a] xb = x[b] xc = x[c] xd = x[d] xa = (xa + xb) & 0xFFFFFFFF tmp = xd ^ xa xd = ((tmp << 16) & 0xFFFFFFFF) | (tmp >> 16) # 16=32-16 xc = (xc + xd) & 0xFFFFFFFF tmp = xb ^ xc xb = ((tmp << 12) & 0xFFFFFFFF) | (tmp >> 20) # 20=32-12 xa = (xa + xb) & 0xFFFFFFFF tmp = xd ^ xa xd = ((tmp << 8) & 0xFFFFFFFF) | (tmp >> 24) # 24=32-8 xc = (xc + xd) & 0xFFFFFFFF tmp = xb ^ xc xb = ((tmp << 7) & 0xFFFFFFFF) | (tmp >> 25) # 25=32-7 x[a] = xa x[b] = xb x[c] = xc x[d] = xd def _xor(self, stream, datain): dataout = [] for i in range(min(len(stream), len(datain))): dataout.append(chr(ord(stream[i]) ^ ord(datain[i]))) return ''.join(dataout) # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - if have_psyco: # if you psyco encrypt() and _chacha_scramble() you # should get a 2.4x speedup over vanilla Python 2.5. # The other functions seem to offer only negligible # improvement. YMMV. _key_setup = psyco.proxy(_key_setup) # small impact iv_setup = psyco.proxy(iv_setup) # small impact encrypt = psyco.proxy(encrypt) # 18-32% _chacha_scramble = psyco.proxy(_chacha_scramble) # big help, 2x _quarterround = psyco.proxy(_quarterround) # ??? # _rotate = psyco.proxy(_rotate) # minor impact _xor = psyco.proxy(_xor) # very small impact pass
>>> def g1(f): ... prep() ... d = f(['file1-basetests', 'BIN:file2-basetests']) ... return [d[chr(n)] for n in range(256)] >>> def protect(f, *args): ... try: ... return f(*args) ... except: ... return 'exception: ' + sys.exc_info()[0].__name__ >>> def assert_true(cond): ... if cond: ... print 'Ok' ... else: ... print 'Assert failed!' >>> True,False = 1==1,1==0 >>> PY21 = sys.hexversion < 0x02020000 >>> if sys.hexversion >= 0x02040000: ... def clamp(x): ... return x ... else: ... def clamp(x): ... if x & (sys.maxint+1L): ... return int(x & sys.maxint) - sys.maxint - 1 ... else: ... return int(x & sys.maxint) ################### #### TEST1 #### ################### >>> print test1.f1(217) 1115467 >>> print test1.f2(0) 0 >>> print test1.f2(-192570368) -385140736 >>> test1.f3([3,4,0,'testing',12.75,(5,3,1),0]) 6 8 testingtesting 25.5 (5, 3, 1, 5, 3, 1) >>> print g1(test1.f5) [20, 14, 19, 9, 12, 25, 13, 9, 17, 23, 289, 26, 15, 13, 17, 19, 23, 18, 15, 14, 18, 22, 14, 18, 18, 17, 21, 27, 21, 20, 15, 12, 1745, 18, 17, 136, 25, 14, 27, 18, 92, 87, 386, 12, 52, 29, 63, 102, 49, 39, 26, 26, 18, 14, 16, 13, 22, 16, 29, 49, 24, 34, 30, 20, 16, 100, 98, 61, 20, 85, 61, 75, 54, 49, 19, 47, 32, 18, 67, 47, 86, 66, 184, 61, 42, 42, 74, 14, 26, 55, 74, 16, 37, 15, 19, 211, 17, 348, 369, 130, 12, 248, 264, 328, 162, 68, 69, 41, 128, 29, 240, 95, 244, 288, 673, 295, 108, 134, 380, 40, 42, 224, 137, 30, 15, 24, 11, 15, 6, 15, 19, 26, 19, 17, 15, 18, 16, 17, 11, 14, 11, 15, 11, 11, 19, 13, 18, 25, 14, 20, 12, 14, 8, 13, 17, 15, 16, 17, 15, 13, 12, 12, 10, 19, 15, 15, 16, 12, 24, 21, 14, 10, 19, 17, 14, 13, 20, 18, 11, 17, 21, 13, 21, 19, 17, 15, 19, 10, 17, 12, 16, 13, 16, 15, 13, 16, 16, 16, 15, 14, 11, 14, 18, 15, 25, 9, 19, 12, 13, 12, 18, 12, 13, 16, 13, 17, 18, 19, 16, 11, 18, 18, 27, 11, 22, 17, 13, 22, 20, 16, 9, 17, 14, 12, 20, 17, 15, 18, 16, 15, 15, 16, 16, 18, 18, 17, 21, 17, 12, 12, 17, 10, 20, 19, 18, 25] >>> assert_true(PY21 or g1(test1.f4) == g1(test1.f5)) Ok >>> print test1.f6(n=100, p=10001) 803 >>> test1.f7(-2-1j, 1+1j, 0.04+0.08j) !!!!!!!""""""####################$$$$$$$$%%%&'*.)+ %$$$$$######"""""""""""" !!!!!!"""""####################$$$$$$$$%%%%&'(+2-)'&%%$$$$$######"""""""""" !!!!!""""###################$$$$$$$$$%%%&&'6E0~ 9=6(&%%%%$$$$######"""""""" !!!!"""###################$$$$$$$$%%&&&&''(+B @('&&%%%%%$$#######"""""" !!!"""##################$$$$$$$%%&(,32)),5+,/M E-,*+)''''-&$$#######""""" !!!"#################$$$$$%%%%%&&&(,b~~/: 0,,:/;/&%$########""" !!"###############$$$%%%%%%%%&&&&()+/? ='&%$$########"" !!"###########$$$%'&&&&%%%&&&&'')U ~ G,('%%$$#######"" !"######$$$$$$%%&&*+)(((2*(''(()2p :@:'%$$########" !###$$$$$$$$%%%%&'(*.IB24 0J,**+~ -(&%$$$######## !#$$$$$$$$%%%%%&'',+2~ // ?*&%$$$######## !$$$$$$$%&&&&'(I+,-j 9 ~*&%%$$$######## !%%&&')''((()-+/S ('&%%$$$$####### !%%&&')''((()-+/S ('&%%$$$$####### !$$$$$$$%&&&&'(I+,-j 9 ~*&%%$$$######## !#$$$$$$$$%%%%%&'',+2~ // ?*&%$$$######## !###$$$$$$$$%%%%&'(*.IB24 0J,**+~ -(&%$$$######## !"######$$$$$$%%&&*+)(((2*(''(()2p :@:'%$$########" !!"###########$$$%'&&&&%%%&&&&'')U ~ G,('%%$$#######"" !!"###############$$$%%%%%%%%&&&&()+/? ='&%$$########"" !!!"#################$$$$$%%%%%&&&(,b~~/: 0,,:/;/&%$########""" !!!"""##################$$$$$$$%%&(,32)),5+,/M E-,*+)''''-&$$#######""""" !!!!"""###################$$$$$$$$%%&&&&''(+B @('&&%%%%%$$#######"""""" !!!!!""""###################$$$$$$$$$%%%&&'6E0~ 9=6(&%%%%$$$$######"""""""" !!!!!!"""""####################$$$$$$$$%%%%&'(+2-)'&%%$$$$$######"""""""""" !!!!!!!""""""####################$$$$$$$$%%%&'*.)+J%$$$$$######"""""""""""" >>> test1.f7bis((-2.0, -1.0), (1.0, 1.0), (0.04, 0.08)) !!!!!!!""""""####################$$$$$$$$%%%&'*.)+ %$$$$$######"""""""""""" !!!!!!"""""####################$$$$$$$$%%%%&'(+2-)'&%%$$$$$######"""""""""" !!!!!""""###################$$$$$$$$$%%%&&'6E0~ 9=6(&%%%%$$$$######"""""""" !!!!"""###################$$$$$$$$%%&&&&''(+B @('&&%%%%%$$#######"""""" !!!"""##################$$$$$$$%%&(,32)),5+,/M E-,*+)''''-&$$#######""""" !!!"#################$$$$$%%%%%&&&(,b~~/: 0,,:/;/&%$########""" !!"###############$$$%%%%%%%%&&&&()+/? ='&%$$########"" !!"###########$$$%'&&&&%%%&&&&'')U ~ G,('%%$$#######"" !"######$$$$$$%%&&*+)(((2*(''(()2p :@:'%$$########" !###$$$$$$$$%%%%&'(*.IB24 0J,**+~ -(&%$$$######## !#$$$$$$$$%%%%%&'',+2~ // ?*&%$$$######## !$$$$$$$%&&&&'(I+,-j 9 ~*&%%$$$######## !%%&&')''((()-+/S ('&%%$$$$####### !%%&&')''((()-+/S ('&%%$$$$####### !$$$$$$$%&&&&'(I+,-j 9 ~*&%%$$$######## !#$$$$$$$$%%%%%&'',+2~ // ?*&%$$$######## !###$$$$$$$$%%%%&'(*.IB24 0J,**+~ -(&%$$$######## !"######$$$$$$%%&&*+)(((2*(''(()2p :@:'%$$########" !!"###########$$$%'&&&&%%%&&&&'')U ~ G,('%%$$#######"" !!"###############$$$%%%%%%%%&&&&()+/? ='&%$$########"" !!!"#################$$$$$%%%%%&&&(,b~~/: 0,,:/;/&%$########""" !!!"""##################$$$$$$$%%&(,32)),5+,/M E-,*+)''''-&$$#######""""" !!!!"""###################$$$$$$$$%%&&&&''(+B @('&&%%%%%$$#######"""""" !!!!!""""###################$$$$$$$$$%%%&&'6E0~ 9=6(&%%%%$$$$######"""""""" !!!!!!"""""####################$$$$$$$$%%%%&'(+2-)'&%%$$$$$######"""""""""" !!!!!!!""""""####################$$$$$$$$%%%&'*.)+J%$$$$$######"""""""""""" >>> print protect(test1.f8) in finally clause exception: ZeroDivisionError >>> test1.f9(50) 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 >>> test1.f10() 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 >>> print test1.f11(50) 950 >>> print test1.f11(-1.0) 1001.0 ################### #### TEST2 #### ################### >>> def f1(): ... return -abs(-10) >>> print f1() -10 >>> def f11(): ... return -abs(-10.125)+5.0+6.0 >>> print f11() 0.875 ################### #### TEST3 #### ################### >>> test3.f11([5,6,7,5,3,5,6,2,5,5,6,7,5]) [0, 0, 0, 1, 0, 1, 2, 0, 1, 1, 2, 3, 4] >>> print test3.f13((None, 'hello')) None hello None hello ('hello', None) >>> print test3.f13([12, 34]) 12 34 12 34 (34, 12) >>> test3.f14(5) ${True} >>> test3.f14(-2) ${False} >>> print test3.f16(123) -124 >>> print test3.f17('abc') ('abc', 0, ()) >>> print test3.f17('abc', 'def', 'ghi', 'jkl') ('abc', 'def', ('ghi', 'jkl')) >>> print test3.f19([1,2,3,4]) hello ${([1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4], True, 0)} >>> print test3.f20('l', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('L', 12) [0L, 10L, 20L, 30L, 40L, 50L, 60L, 70L, 80L, 90L, 100L, 110L] >>> print test3.f20('i', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('I', 12) [0L, 10L, 20L, 30L, 40L, 50L, 60L, 70L, 80L, 90L, 100L, 110L] >>> print test3.f20('c', 12, 'x') ['\x00', '\n', '\x14', '\x1e', '(', '2', '<', 'F', 'P', 'Z', 'd', 'n'] >>> print test3.f20('b', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('B', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('h', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('H', 12) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110] >>> print test3.f20('B', 17) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150, 160] >>> print test3.f20('h', 28) [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150, 160, 170, 180, 190, 200, 210, 220, 230, 240, 250, 260, 270] >>> print test3.f21([2,6,'never',9,3,0.123]) 3 >>> test3.f22(0) Catch! >>> print test3.f22(-2.0) None >>> test3.f23(0.0) Catch! Catch! NameError >>> test3.f23(23) NameError >>> print [x.__name__ for x in test3.f26()] ['float', 'list', 'urllib', 'psyco.classes', 'full'] >>> test3.N=5; print test3.f28(), test3.f28_1(), test3.f28_b(), test3.f28_b1() test_getframe(): test_getframe f28 ? 5 test_getframe(): test_getframe test_getframe1 f28_1 ? 5 test_getframe_b(): test_getframe_b f28_b ? 5 test_getframe_b(): test_getframe_b test_getframe_b1 f28_b1 ? 5 >>> print test3.f27(), test3.f27_1(), test3.f27_b(), test3.f27_b1() test_getframe(): test_getframe f28 f27 ? test_getframe(): test_getframe f28 f27 ? test_getframe(): test_getframe f28 f27 ? (5, 6, 7) test_getframe(): test_getframe test_getframe1 f28_1 f27_1 ? test_getframe(): test_getframe test_getframe1 f28_1 f27_1 ? test_getframe(): test_getframe test_getframe1 f28_1 f27_1 ? (51, 61, 71) test_getframe_b(): test_getframe_b f28_b f27_b ? test_getframe_b(): test_getframe_b f28_b f27_b ? test_getframe_b(): test_getframe_b f28_b f27_b ? (95, 96, 97) test_getframe_b(): test_getframe_b test_getframe_b1 f28_b1 f27_b1 ? test_getframe_b(): test_getframe_b test_getframe_b1 f28_b1 f27_b1 ? test_getframe_b(): test_getframe_b test_getframe_b1 f28_b1 f27_b1 ? (951, 961, 971) >>> print test3.f29(range(10,0,-1)) [10, 9, 7, 6, 5, 4, 3, 2, 1] >>> print test3.f32('c:/temp') ('c:', '/temp') >>> print test3.f32('*') ('', '*') >>> print test3.f32('/dev/null') ('', '/dev/null') >>> test3.f33(31) 31 >>> print test3.f33(33) None >>> print test3.f33(32) None >>> test3.f34(70000) 0 1 3 7 15 31 63 127 255 511 1023 2047 4095 8191 16383 32767 65535 >>> test3.f35() [[5 5 5] [5 5 5] [5 5 5]] >>> test3.f37(None) ${True} 1 >>> print test3.f38(12) [234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234, 234] ################### #### TEST5 #### ################### >>> print hash(test5.f('file1-basetests')) 33961417 >>> prep(); print hash(test5.f('file2-basetests', 'rb')) 2034921519 >>> print test5.f2(4,5,6) (6, 5, 4) >>> print test5.f2(4,5,(6,)) (6, 5, 4) >>> assert_true(test5.f3(15, 32) == (clamp(64424509440L), 30, ... clamp(32212254720L), 0, 7, 0)) Ok >>> assert_true(test5.f3(15, 31) == (clamp(32212254720L), 30, ... clamp(32212254720L), 0, 7, 0)) Ok >>> assert_true(test5.f3(15, 33) == (clamp(128849018880L), 30, ... clamp(32212254720L), 0, 7, 0)) Ok >>> assert_true(test5.f3(15, 63) == (clamp(138350580552821637120L), 30, ... clamp(32212254720L), 0, 7, 0)) Ok >>> assert_true(test5.f3(-15, 63) == (clamp(-138350580552821637120L), -30, ... clamp(-32212254720L), -1, -8, -1)) Ok >>> assert_true(test5.f3(-15, 32) == (clamp(-64424509440L), -30, ... clamp(-32212254720L), -1, -8, -1)) Ok >>> assert_true(test5.f3(-15, 31) == (clamp(-32212254720L), -30, ... clamp(-32212254720L), -1, -8, -1)) Ok >>> assert_true(test5.f3(-15, 33) == (clamp(-128849018880L), -30, ... clamp(-32212254720L), -1, -8, -1)) Ok >>> assert_true(test5.f3(-15, 2) == (-60, -30, ... clamp(-32212254720L), -4, -8, -1)) Ok >>> assert_true(test5.f3(-15, 1) == (-30, -30, ... clamp(-32212254720L), -8, -8, -1)) Ok >>> assert_true(test5.f3(-15, 0) == (-15, -30, ... clamp(-32212254720L), -15, -8, -1)) Ok >>> assert_true(test5.f3(15, 0) == (15, 30, ... clamp(32212254720L), 15, 7, 0)) Ok >>> assert_true(test5.f3(15, 1) == (30, 30, ... clamp(32212254720L), 7, 7, 0)) Ok >>> assert_true(test5.f3(15, 2) == (60, 30, ... clamp(32212254720L), 3, 7, 0)) Ok >>> assert_true(test5.f3(-1, 0) == (-1, -2, -2147483648L, -1, -1, -1)) Ok >>> print test5.f4("some-string") abcsome-string >>> print test5.overflowtest() -3851407362L >>> test5.booltest() ${False} ${True} ${False} ${True} ${False} ${True} ${[a & b for a in (False,True) for b in (False,True)]} ${[a | b for a in (False,True) for b in (False,True)]} ${[a ^ b for a in (False,True) for b in (False,True)]} ${True} >>> test5.exc_test() IndexError list index out of range 2 >>> test5.seqrepeat() 'abcabcabcabcabc' 'abcabcabcabcabc' [3, 'z', 3, 'z', 3, 'z', 3, 'z', 3, 'z'] [6, 3, 6, 3, 6, 3, 6, 3, 6, 3] 'yyyyyx' 'abcabcabcabcabcabc' 'abcabcabcabcabcabc' [3, 'z', 3, 'z', 3, 'z', 3, 'z', 3, 'z', 3, 'z'] [6, 3, 6, 3, 6, 3, 6, 3, 6, 3, 6, 3] 'yyyyyyx' '' '' [] [] 'x' >>> test5.f5(99) 100 100 4 100 >>> test5.f5(-3.0) -2.0 -2.0 4 -2.0 >>> test5.f6(3) None None None None 5 >>> test5.f6(-2) -1 -1 None -1 48 >>> test5.f6(99) 100 100 None 100 IndexError >>> test5.f6("error") TypeError >>> test5.f7(8) [8, 75, 121] [8, 15, 11] >>> test5.f7(8.5) [8.5, 75, 121] [8.5, 15, 11] >>> test5.f8(8) [0, 30, 44] [0.0, 0.0, 0.0] >>> test5.f8(8.5) [0.0, 30, 44] [0.0, 0.0, 0.0] >>> print test5.f9(10) (4, 11) >>> assert_true(PY21 or test5.f9(sys.maxint) == (4, 2147483648L)) Ok >>> test5.teststrings() 'userhruuiadsfz1if623opadoa8ua09q34rx093q\x00qw09exdqw0e9dqw9e8d8qw9r8qw\x1d\xd7\xae\xa2\x06\x10\x1a\x00a\xff\xf6\xee\x15\xa2\xea\x89akjsdfhqweirewru 3498cr 3849rx398du389du389dur398d31623' 'someanother' 'userhru.' '.userhru' 'userhruuiadsfz' 'akjsdfhqweirewru 3498cr 3849rx398du389du389dur398d31623\x1d\xd7\xae\xa2\x06\x10\x1a\x00a\xff\xf6\xee\x15\xa2\xea\x89qw09exdqw0e9dqw9e8d8qw9r8qw\x0009q34rx093qoa8uaopad623if1uiadsfzuserhru' 1 'a' 'sdfhqweirewru 3498cr 3849rx398du389du389dur398d3' 1 1 0 1 >>> test5.testslices('hello') '' 'hello' 'hello' '' 'hello' 'hello' '' 'ello' 'ello' '' '' '' >>> test5.testovf(1987654321, 2012345789) 4000000110 4012345789 3987654321 -24691468 -12345789 -12345679 3999847802852004269 4024691578000000000 3975308642000000000 1987654321 -1987654321 1987654321 >>> test5.testovf(-2147483647-1, 2012345789) -135137859 4012345789 -147483648 -4159829437 -12345789 -4147483648 -4321479675999158272 4024691578000000000 -4294967296000000000 -2147483648 2147483648 2147483648 >>> test5.testovf(-2147483647-1, -2147483647-1) -4294967296 -147483648 -147483648 0 4147483648 -4147483648 4611686018427387904 -4294967296000000000 -4294967296000000000 -2147483648 2147483648 2147483648 >>> test5.rangetypetest(12) list list list xrange xrange xrange >>> test5.rangetest(15) 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 10 11 12 13 14 15 14 13 12 11 >>> test5.xrangetest(15) 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 10 11 12 13 14 15 14 13 12 11 >>> test5.longrangetest() [1234567890123456789L, 1234567890123456790L] >>> print list(xrange(10)) [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] >>> x = xrange(10); print sys.getrefcount(x); print list(x) 2 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9] >>> print list(xrange(-2, 5)) [-2, -1, 0, 1, 2, 3, 4] >>> print list(xrange(-2, 5, 2)) [-2, 0, 2, 4] >>> print list(xrange(-2, 5, -2)) [] >>> print list(xrange(5, -2, -2)) [5, 3, 1, -1] >>> test5.arraytest() S >>> test5.proxy_defargs() 12 >>> test5.setfilter() ('f1', 1) ('f2', 0) >>> test5.makeSelection() do stuff here >>> test5.class_creation_1(1111) ok >>> test5.class_creation_2(1111) ok >>> test5.class_creation_3() ok >>> test5.class_creation_4(1111) ok >>> test5.power_int(1) 332833500 >>> test5.power_int(10) 332833500 >>> test5.power_int_long(1) long 332833500 >>> test5.power_int_long(10) long 332833500 >>> test5.power_float(1) float 7038164 >>> test5.power_float(10) float 7038164 >>> test5.conditional_doubletest_fold() ok(1) ok(2) >>> test5.importname(['ab', 'cd', 'ef']) Ok >>> test5.sharedlists(3); test5.sharedlists(12) 4 8 >>> test5.variousslices() slice(4, None, None) slice(None, 7, None) slice(9, 'hello', None) slice('world', None, None) slice(1, 10, 'hello') 4 2147483647 0 7 slice(9, 'hello', None) slice('world', None, None) slice(1, 10, 'hello') >>> test5.listgetitem() foobar Ok >>> test5.negintpow(8) 0.015625 ########################### #### COMPACTOBJECT #### ########################### >>> for i in range(5): print compactobject.do_test(i) or i 0 1 2 3 4 >>> for i in range(5, 10): ... compactobject.do_test(i, ... do_test_1=psyco.proxy(compactobject.do_test_1)) ... print i 5 6 7 8 9 >>> compactobject.pcompact_test() 13 hello None >>> compactobject.pcompact_creat('hel' + 'lo') (0, 0, 0) 3 None hello (0, 1, 2) 4 None hello (0, 2, 4) 5 None hello (0, 3, 6) 6 None hello (0, 4, 8) 7 None hello (0, 5, 10) 8 None hello (0, 6, 12) 9 None hello (0, 7, 14) 10 None hello (0, 8, 16) 11 None hello (0, 9, 18) 12 None hello (0, 10, 20) 13 None hello 11 0 >>> compactobject.pcompact_modif('hel' + 'lo') hello 1 0 1 hello 1 0 2 hello 1 0 3 hello 1 0 4 hello 1 0 5 hello 1 0 6 hello 1 0 7 hello 1 0 8 hello 1 0 9 hello 1 0 10 hello 1 0 11 hello 1 0 12 hello 1 0 13 hello 1 0 14 hello 1 0 15 hello 1 0 16 hello 1 0 17 hello 1 0 18 hello 1 0 19 hello 1 0 20 hello 1 0 21 0
has_numba = True except ImportError: print 'No numba found doing tests without it.' import measure_time #4 from plain_pi import pi_plain #5 from math_pi import pi_math from pool_pi import calc_pi_workers if has_numpy: from numpy_pi import pi_numpy from pool_numpy_pi import calc_pi_workers_numpy if has_psyco: psyco_pi_plain = psyco.proxy(pi_plain) #6 psyco_pi_math = psyco.proxy(pi_math) psyco_calc_pi_workers = psyco.proxy(calc_pi_workers) if has_numpy: psyco_pi_numpy = psyco.proxy(pi_numpy) psyco_calc_pi_workers_numpy = psyco.proxy(calc_pi_workers_numpy) if has_numba: from numba_pi import pi_numba_auto, pi_numba, jitted_pi, jitted_pi_auto def main(): """Run all tests that could be found. """ total = int(float(sys.argv[1])) #7 repeat = int(sys.argv[2]) #8
def __proxy_t(f): return psyco.proxy(f)
def listgetitem(): class X(list): def __getitem__(self, key): return key x = X(["Ok"]) print x["foobar"] for item in x: print item def negintpow(x): print x**-2 if __name__ == '__main__': from test1 import go, print_results import time print "break!" time.sleep(0.5) #go(class_creation_1) #go(class_creation_2) #go(class_creation_3) #go(class_creation_4) #go(power_int) #go(power_int_long) #go(power_float) psyco.proxy(negintpow)(8) psyco.dumpcodebuf() print_results()
print ch for tau in range(total_offset): ldif_a = epochs[7, interest_region, ch, :].flatten() ldif_b = epochs[7, interest_region+tau, ch, :].flatten() dlif_a = epochs[3, interest_region, ch, :].flatten() dlif_b = epochs[3, interest_region+tau, ch, :].flatten() ami_ldif[ch, tau] = mi(ldif_a, ldif_b, bins=bins) ami_dlif[ch, tau] = mi(dlif_a, dlif_b, bins=bins) return ami_ldif, ami_dlif if __name__ == "__main__": epochs = numpy.load("epochs.npy") import psyco histogram2d = psyco.proxy(numpy.histogram2d) # Transform the data to emphasize power. # This is something to play around with. epochs = abs(epochs)**2 # Constants. bins = 64 n_chan = 157 total_offset = 150 interest_region = arange(250, 450+1) print "Computing cross mutual information" mi_ldif, mi_dlif = cross_mi(epochs, interest_region, n_chan, bins) #print "Computing auto mutual information with time shifts"
def proxy(function): return psyco.proxy(function)
class Salsa20(object): """ Salsa20 was submitted to eSTREAM, an EU stream cipher competition). Salsa20 was originally defined to be 20 rounds. Reduced round versions, Salsa20/8 (8 rounds) and Salsa20/12 (12 rounds), were also submitted. Salsa20/12 was chosen as one of the winners and 12 rounds was deemed the "right blend" of security and efficiency. The default for this class is 20 rounds. Besides the encryption function and the decryption function being identical, exactly how Salsa20 works is very simple. Salsa20 accepts a key and an iv to set up an initial 64-byte state. For each 64-byte block of data, the state gets scrambled and XORed with the previous state. This new state is then XORed with the input data to produce the output. Salsa20's security is achieved via this one scrambling operation, repeated n times (rounds). Sample usage: s20 = Salsa20(key, iv, 12) ciphertext = s20.encrypt(message) Larry Bugbee May 2009 """ TAU = (0x61707865, 0x3120646e, 0x79622d36, 0x6b206574) SIGMA = (0x61707865, 0x3320646e, 0x79622d32, 0x6b206574) ROUNDS = 20 # 8, 12, 20 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def __init__(self, key, iv='\x00' * 8, rounds=ROUNDS): """ Both key and iv are bytestrings. The key must be exactly 16 or 32 bytes, 128 or 256 bits respectively. The iv must be exactly 8 bytes (64 bits). Setting the key but relying on a default iv value (nulls) is dangerous. Either provide the iv here or explicitly call iv_setup() to set the iv. Salsa20 exists in three basic versions defined by the number of rounds (8, 12, and 20). 20 rounds, Salsa20, is the default. 12 rounds, Salsa20/12, is the version selected by eSTREAM. The 8 round version, Salsa20/8 is faster and remains unbroken, but the lesser rounds reduces confidence. Salsa20/8 should not be used with high value assets. The default number of rounds is 12. """ self._key_setup(key) self.iv_setup(iv) if rounds not in [20, 12, 8]: raise Exception('number of rounds must be 8, 12, or 20') self.ROUNDS = rounds # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def _key_setup(self, key): """ key is converted to a list of 4-byte unsigned integers (32 bits). Calling this routine with a key value effectively resets the context/instance. Be sure to set the iv as well. """ if len(key) not in [16, 32]: raise Exception('key must be either 16 or 32 bytes') TAU = self.TAU SIGMA = self.SIGMA key_state = [0] * 16 if len(key) == 16: k = list(struct.unpack('<4I', key)) key_state[0] = TAU[0] key_state[1] = k[0] key_state[2] = k[1] key_state[3] = k[2] key_state[4] = k[3] key_state[5] = TAU[1] key_state[10] = TAU[2] key_state[11] = k[0] key_state[12] = k[1] key_state[13] = k[2] key_state[14] = k[3] key_state[15] = TAU[3] elif len(key) == 32: k = list(struct.unpack('<8I', key)) key_state[0] = SIGMA[0] key_state[1] = k[0] key_state[2] = k[1] key_state[3] = k[2] key_state[4] = k[3] key_state[5] = SIGMA[1] key_state[10] = SIGMA[2] key_state[11] = k[4] key_state[12] = k[5] key_state[13] = k[6] key_state[14] = k[7] key_state[15] = SIGMA[3] self.key_state = key_state # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def iv_setup(self, iv): """ self.state and other working strucures are lists of 4-byte unsigned integers (32 bits). The iv should never be reused with the same key value, but it is not a secret. Use date, time or some other counter to be sure the iv is different each time, and be sure to communicate the IV to the receiving party. Prepending 8 bytes of iv to the ciphertext is the usual way to do this. Just as setting a new key value effectively resets the context, setting the iv also resets the context with the last key value entered. """ if len(iv) != 8: raise Exception('iv must be 8 bytes') iv_state = self.key_state[:] v = list(struct.unpack('<2I', iv)) iv_state[6] = v[0] iv_state[7] = v[1] iv_state[8] = 0 iv_state[9] = 0 self.state = iv_state self.lastchunk = 64 # flag to ensure all but the last # chunks is a multiple of 64 bytes # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def encrypt(self, datain): """ datain and dataout are bytestrings. If the data is submitted to this routine in chunks, the chunk size MUST be an exact multiple of 64 bytes. Only the final chunk may be less than an even multiple. """ if self.lastchunk != 64: raise Exception('size of last chunk not a multiple of 64 bytes') dataout = '' stream = '' while datain: stream = self._salsa20_scramble() self.state[8] += 1 if self.state[8] == 0: # if overflow in state[8] self.state[9] += 1 # carry to state[9] # not to exceed 2^70 x 2^64 = 2^134 data size ??? <<<< dataout += self._xor(stream, datain[:64]) if len(datain) <= 64: self.lastchunk = len(datain) return dataout datain = datain[64:] raise Exception('Huh?') decrypt = encrypt # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def _ROL32(self, a, b): return ((a << b) | (a >> (32 - b))) & 0xffffffff def quarterround(self, x): assert len(x) == 4 # x[1] ^= self._ROL32( (x[0]+x[3]) & 0xffffffff, 7) # x[2] ^= self._ROL32( (x[1]+x[0]) & 0xffffffff, 9) # x[3] ^= self._ROL32( (x[2]+x[1]) & 0xffffffff, 13) # x[0] ^= self._ROL32( (x[3]+x[2]) & 0xffffffff, 18) x[1] = (x[1] + x[2]) & 0xffffffff x[1] = (x[1] + x[3]) & 0xffffffff x[0] = self._ROL32(x[0], 7) x[0] = x[0] ^ x[3] x[3] = x[3] ^ x[1] x[0] = x[0] ^ x[3] x[1] = (x[1] + x[2]) & 0xffffffff x[1] = self._ROL32(x[1], 6) x[3] = self._ROL32(x[3], 16) x[1] = (x[1] + x[3]) & 0xffffffff x[1] = self._ROL32(x[1], 13) x[1] = self._ROL32(x[1], 10) return x def _salsa20_scramble(self): # 64 bytes in """ self.state and other working strucures are lists of 4-byte unsigned integers (32 bits). output must be converted to bytestring before return. """ x = self.state[:] # makes a copy for i in range(self.ROUNDS, 0, -2): # x[ 4] ^= self._ROL32( (x[ 0]+x[12]) & 0xffffffff, 7) # x[ 8] ^= self._ROL32( (x[ 4]+x[ 0]) & 0xffffffff, 9) # x[12] ^= self._ROL32( (x[ 8]+x[ 4]) & 0xffffffff, 13) # x[ 0] ^= self._ROL32( (x[12]+x[ 8]) & 0xffffffff, 18) x[0], x[4], x[8], x[12] = self.quarterround( [x[0], x[4], x[8], x[12]]) # x[ 9] ^= self._ROL32( (x[ 5]+x[ 1]) & 0xffffffff, 7) # x[13] ^= self._ROL32( (x[ 9]+x[ 5]) & 0xffffffff, 9) # x[ 1] ^= self._ROL32( (x[13]+x[ 9]) & 0xffffffff, 13) # x[ 5] ^= self._ROL32( (x[ 1]+x[13]) & 0xffffffff, 18) x[5], x[9], x[13], x[1] = self.quarterround( [x[5], x[9], x[13], x[1]]) # x[14] ^= self._ROL32( (x[10]+x[ 6]) & 0xffffffff, 7) # x[ 2] ^= self._ROL32( (x[14]+x[10]) & 0xffffffff, 9) # x[ 6] ^= self._ROL32( (x[ 2]+x[14]) & 0xffffffff, 13) # x[10] ^= self._ROL32( (x[ 6]+x[ 2]) & 0xffffffff, 18) x[10], x[14], x[2], x[6] = self.quarterround( [x[10], x[14], x[2], x[6]]) # x[ 3] ^= self._ROL32( (x[15]+x[11]) & 0xffffffff, 7) # x[ 7] ^= self._ROL32( (x[ 3]+x[15]) & 0xffffffff, 9) # x[11] ^= self._ROL32( (x[ 7]+x[ 3]) & 0xffffffff, 13) # x[15] ^= self._ROL32( (x[11]+x[ 7]) & 0xffffffff, 18) x[15], x[3], x[7], x[11] = self.quarterround( [x[15], x[3], x[7], x[11]]) # x[ 1] ^= self._ROL32( (x[ 0]+x[ 3]) & 0xffffffff, 7) # x[ 2] ^= self._ROL32( (x[ 1]+x[ 0]) & 0xffffffff, 9) # x[ 3] ^= self._ROL32( (x[ 2]+x[ 1]) & 0xffffffff, 13) # x[ 0] ^= self._ROL32( (x[ 3]+x[ 2]) & 0xffffffff, 18) x[0], x[1], x[2], x[3] = self.quarterround( [x[0], x[1], x[2], x[3]]) # x[ 6] ^= self._ROL32( (x[ 5]+x[ 4]) & 0xffffffff, 7) # x[ 7] ^= self._ROL32( (x[ 6]+x[ 5]) & 0xffffffff, 9) # x[ 4] ^= self._ROL32( (x[ 7]+x[ 6]) & 0xffffffff, 13) # x[ 5] ^= self._ROL32( (x[ 4]+x[ 7]) & 0xffffffff, 18) x[5], x[6], x[7], x[4] = self.quarterround( [x[5], x[6], x[7], x[4]]) # x[11] ^= self._ROL32( (x[10]+x[ 9]) & 0xffffffff, 7) # x[ 8] ^= self._ROL32( (x[11]+x[10]) & 0xffffffff, 9) # x[ 9] ^= self._ROL32( (x[ 8]+x[11]) & 0xffffffff, 13) # x[10] ^= self._ROL32( (x[ 9]+x[ 8]) & 0xffffffff, 18) x[10], x[11], x[8], x[9] = self.quarterround( [x[10], x[11], x[8], x[9]]) # x[12] ^= self._ROL32( (x[15]+x[14]) & 0xffffffff, 7) # x[13] ^= self._ROL32( (x[12]+x[15]) & 0xffffffff, 9) # x[14] ^= self._ROL32( (x[13]+x[12]) & 0xffffffff, 13) # x[15] ^= self._ROL32( (x[14]+x[13]) & 0xffffffff, 18) x[15], x[12], x[13], x[14] = self.quarterround( [x[15], x[12], x[13], x[14]]) for i in range(16): x[i] = (x[i] + self.state[i]) & 0xffffffff output = struct.pack('<16I', x[0], x[1], x[2], x[3], x[4], x[5], x[6], x[7], x[8], x[9], x[10], x[11], x[12], x[13], x[14], x[15]) return output # 64 bytes out # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - def _xor(self, stream, din): dout = [] for i in range(len(din)): dout.append(chr(ord(stream[i]) ^ ord(din[i]))) return ''.join(dout) if have_psyco: # _key_setup = psyco.proxy(_key_setup) # doesn't have much effect # encrypt = psyco.proxy(encrypt) # doesn't have much effect _ROL32 = psyco.proxy(_ROL32) # minor impact _salsa20_scramble = psyco.proxy(_salsa20_scramble) # big help, 2x _xor = psyco.proxy(_xor) # very small impact
for tau in range(total_offset): ldif_a = epochs[7, interest_region, ch, :].flatten() ldif_b = epochs[7, interest_region + tau, ch, :].flatten() dlif_a = epochs[3, interest_region, ch, :].flatten() dlif_b = epochs[3, interest_region + tau, ch, :].flatten() ami_ldif[ch, tau] = mi(ldif_a, ldif_b, bins=bins) ami_dlif[ch, tau] = mi(dlif_a, dlif_b, bins=bins) return ami_ldif, ami_dlif if __name__ == "__main__": epochs = numpy.load("epochs.npy") import psyco histogram2d = psyco.proxy(numpy.histogram2d) # Transform the data to emphasize power. # This is something to play around with. epochs = abs(epochs)**2 # Constants. bins = 64 n_chan = 157 total_offset = 150 interest_region = arange(250, 450 + 1) print "Computing cross mutual information" mi_ldif, mi_dlif = cross_mi(epochs, interest_region, n_chan, bins) #print "Computing auto mutual information with time shifts"
class PyDBFrame: '''This makes the tracing for a given frame, so, the trace_dispatch is used initially when we enter into a new context ('call') and then is reused for the entire context. ''' def __init__(self, args): #args = mainDebugger, filename, base, info, t, frame #yeap, much faster than putting in self and then getting it from self later on self._args = args[:-1] def setSuspend(self, *args, **kwargs): self._args[0].setSuspend(*args, **kwargs) def doWaitSuspend(self, *args, **kwargs): self._args[0].doWaitSuspend(*args, **kwargs) def trace_exception(self, frame, event, arg): if event == 'exception': (flag, frame) = self.shouldStopOnException(frame, event, arg) if flag: self.handle_exception(frame, event, arg) return self.trace_dispatch return self.trace_exception def shouldStopOnException(self, frame, event, arg): mainDebugger, filename, info, thread = self._args flag = False if info.pydev_state != STATE_SUSPEND: #and breakpoint is not None: (exception, value, trace) = arg if trace is not None: #on jython trace is None on the first event exception_breakpoint = get_exception_breakpoint( exception, dict(mainDebugger.exception_set), NOTIFY_ALWAYS) if exception_breakpoint is not None: if not exception_breakpoint.notify_on_first_raise_only or just_raised( trace): curr_func_name = frame.f_code.co_name add_exception_to_frame(frame, (exception, value, trace)) self.setSuspend(thread, CMD_ADD_EXCEPTION_BREAK) thread.additionalInfo.message = exception_breakpoint.qname flag = True else: flag = False else: try: if mainDebugger.django_exception_break and get_exception_name( exception) in [ 'VariableDoesNotExist', 'TemplateDoesNotExist', 'TemplateSyntaxError' ] and just_raised( trace ) and is_django_exception_break_context(frame): render_frame = find_django_render_frame(frame) if render_frame: suspend_frame = suspend_django( self, mainDebugger, thread, render_frame, CMD_ADD_DJANGO_EXCEPTION_BREAK) if suspend_frame: add_exception_to_frame( suspend_frame, (exception, value, trace)) flag = True thread.additionalInfo.message = 'VariableDoesNotExist' suspend_frame.f_back = frame frame = suspend_frame except: flag = False return (flag, frame) def handle_exception(self, frame, event, arg): mainDebugger = self._args[0] thread = self._args[3] self.doWaitSuspend(thread, frame, event, arg) mainDebugger.SetTraceForFrameAndParents(frame) def trace_dispatch(self, frame, event, arg): mainDebugger, filename, info, thread = self._args try: info.is_tracing = True if mainDebugger._finishDebuggingSession: return None if getattr(thread, 'pydev_do_not_trace', None): return None if event == 'call': sendSignatureCallTrace(mainDebugger, frame, filename) if event not in ('line', 'call', 'return'): if event == 'exception': (flag, frame) = self.shouldStopOnException(frame, event, arg) if flag: self.handle_exception(frame, event, arg) return self.trace_dispatch else: #I believe this can only happen in jython on some frontiers on jython and java code, which we don't want to trace. return None if event is not 'exception': breakpoints_for_file = mainDebugger.breakpoints.get(filename) can_skip = False if info.pydev_state == STATE_RUN: #we can skip if: #- we have no stop marked #- we should make a step return/step over and we're not in the current frame can_skip = (info.pydev_step_cmd is None and info.pydev_step_stop is None)\ or (info.pydev_step_cmd in (CMD_STEP_RETURN, CMD_STEP_OVER) and info.pydev_step_stop is not frame) if mainDebugger.django_breakpoints: can_skip = False # Let's check to see if we are in a function that has a breakpoint. If we don't have a breakpoint, # we will return nothing for the next trace #also, after we hit a breakpoint and go to some other debugging state, we have to force the set trace anyway, #so, that's why the additional checks are there. if not breakpoints_for_file: if can_skip: if mainDebugger.always_exception_set or mainDebugger.django_exception_break: return self.trace_exception else: return None else: #checks the breakpoint to see if there is a context match in some function curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' for breakpoint in breakpoints_for_file.values( ): #jython does not support itervalues() #will match either global or some function if breakpoint.func_name in ('None', curr_func_name): break else: # if we had some break, it won't get here (so, that's a context that we want to skip) if can_skip: #print 'skipping', frame.f_lineno, info.pydev_state, info.pydev_step_stop, info.pydev_step_cmd return None else: breakpoints_for_file = None #We may have hit a breakpoint or we are already in step mode. Either way, let's check what we should do in this frame #print 'NOT skipped', frame.f_lineno, frame.f_code.co_name, event try: line = frame.f_lineno flag = False if event == 'call' and info.pydev_state != STATE_SUSPEND and mainDebugger.django_breakpoints \ and is_django_render_call(frame): (flag, frame) = self.shouldStopOnDjangoBreak(frame, event, arg) #return is not taken into account for breakpoint hit because we'd have a double-hit in this case #(one for the line and the other for the return). if not flag and event != 'return' and info.pydev_state != STATE_SUSPEND and breakpoints_for_file is not None\ and DictContains(breakpoints_for_file, line): #ok, hit breakpoint, now, we have to discover if it is a conditional breakpoint # lets do the conditional stuff here breakpoint = breakpoints_for_file[line] stop = True if info.pydev_step_cmd == CMD_STEP_OVER and info.pydev_step_stop is frame and event in ( 'line', 'return'): stop = False #we don't stop on breakpoint if we have to stop by step-over (it will be processed later) else: if breakpoint.condition is not None: try: val = eval(breakpoint.condition, frame.f_globals, frame.f_locals) if not val: return self.trace_dispatch except: pydev_log.info( 'Error while evaluating condition \'%s\': %s\n' % (breakpoint.condition, sys.exc_info()[1])) return self.trace_dispatch if breakpoint.expression is not None: try: try: val = eval(breakpoint.expression, frame.f_globals, frame.f_locals) except: val = sys.exc_info()[1] finally: if val is not None: thread.additionalInfo.message = val if stop: self.setSuspend(thread, CMD_SET_BREAK) # if thread has a suspend flag, we suspend with a busy wait if info.pydev_state == STATE_SUSPEND: self.doWaitSuspend(thread, frame, event, arg) return self.trace_dispatch except: raise #step handling. We stop when we hit the right frame try: django_stop = False if info.pydev_step_cmd == CMD_STEP_INTO: stop = event in ('line', 'return') if is_django_suspended(thread): #django_stop = event == 'call' and is_django_render_call(frame) stop = stop and is_django_resolve_call( frame.f_back ) and not is_django_context_get_call(frame) if stop: info.pydev_django_resolve_frame = 1 #we remember that we've go into python code from django rendering frame elif info.pydev_step_cmd == CMD_STEP_OVER: if is_django_suspended(thread): django_stop = event == 'call' and is_django_render_call( frame) stop = False else: if event == 'return' and info.pydev_django_resolve_frame is not None and is_django_resolve_call( frame.f_back): #we return to Django suspend mode and should not stop before django rendering frame info.pydev_step_stop = info.pydev_django_resolve_frame info.pydev_django_resolve_frame = None thread.additionalInfo.suspend_type = DJANGO_SUSPEND stop = info.pydev_step_stop is frame and event in ( 'line', 'return') elif info.pydev_step_cmd == CMD_SMART_STEP_INTO: stop = False if info.pydev_smart_step_stop is frame: info.pydev_func_name = None info.pydev_smart_step_stop = None if event == 'line' or event == 'exception': curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ( '?', '<module>') or curr_func_name is None: curr_func_name = '' if curr_func_name == info.pydev_func_name: stop = True elif info.pydev_step_cmd == CMD_STEP_RETURN: stop = event == 'return' and info.pydev_step_stop is frame elif info.pydev_step_cmd == CMD_RUN_TO_LINE or info.pydev_step_cmd == CMD_SET_NEXT_STATEMENT: stop = False if event == 'line' or event == 'exception': #Yes, we can only act on line events (weird hum?) #Note: This code is duplicated at pydevd.py #Acting on exception events after debugger breaks with exception curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' if curr_func_name == info.pydev_func_name: line = info.pydev_next_line if frame.f_lineno == line: stop = True else: if frame.f_trace is None: frame.f_trace = self.trace_dispatch frame.f_lineno = line frame.f_trace = None stop = True else: stop = False if django_stop: frame = suspend_django(self, mainDebugger, thread, frame) if frame: self.doWaitSuspend(thread, frame, event, arg) elif stop: #event is always == line or return at this point if event == 'line': self.setSuspend(thread, info.pydev_step_cmd) self.doWaitSuspend(thread, frame, event, arg) else: #return event back = frame.f_back if back is not None: #When we get to the pydevd run function, the debugging has actually finished for the main thread #(note that it can still go on for other threads, but for this one, we just make it finish) #So, just setting it to None should be OK if basename( back.f_code.co_filename ) == 'pydevd.py' and back.f_code.co_name == 'run': back = None if back is not None: #if we're in a return, we want it to appear to the user in the previous frame! self.setSuspend(thread, info.pydev_step_cmd) self.doWaitSuspend(thread, back, event, arg) else: #in jython we may not have a back frame info.pydev_step_stop = None info.pydev_step_cmd = None info.pydev_state = STATE_RUN except: traceback.print_exc() info.pydev_step_cmd = None #if we are quitting, let's stop the tracing retVal = None if not mainDebugger.quitting: retVal = self.trace_dispatch return retVal finally: info.is_tracing = False #end trace_dispatch if USE_PSYCO_OPTIMIZATION: try: import psyco trace_dispatch = psyco.proxy(trace_dispatch) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear() #don't keep the traceback pass #ok, psyco not available def shouldStopOnDjangoBreak(self, frame, event, arg): mainDebugger, filename, info, thread = self._args flag = False filename = get_template_file_name(frame) pydev_log.debug("Django is rendering a template: %s\n" % filename) django_breakpoints_for_file = mainDebugger.django_breakpoints.get( filename) if django_breakpoints_for_file: pydev_log.debug("Breakpoints for that file: %s\n" % django_breakpoints_for_file) template_line = get_template_line(frame) pydev_log.debug("Tracing template line: %d\n" % template_line) if DictContains(django_breakpoints_for_file, template_line): django_breakpoint = django_breakpoints_for_file[template_line] if django_breakpoint.is_triggered(frame): pydev_log.debug("Breakpoint is triggered.\n") flag = True new_frame = DjangoTemplateFrame(frame) if django_breakpoint.condition is not None: try: val = eval(django_breakpoint.condition, new_frame.f_globals, new_frame.f_locals) if not val: flag = False pydev_log.debug( "Condition '%s' is evaluated to %s. Not suspending.\n" % (django_breakpoint.condition, val)) except: pydev_log.info( 'Error while evaluating condition \'%s\': %s\n' % (django_breakpoint.condition, sys.exc_info()[1])) if django_breakpoint.expression is not None: try: try: val = eval(django_breakpoint.expression, new_frame.f_globals, new_frame.f_locals) except: val = sys.exc_info()[1] finally: if val is not None: thread.additionalInfo.message = val if flag: frame = suspend_django(self, mainDebugger, thread, frame) return (flag, frame)
if isinstance(value, unicode): value = value.encode('utf-8') else: if isinstance(value, bytes): value = value.encode('utf-8') except TypeError: #in java, unicode is a function pass xmlValue = ' value="%s"' % (makeValidXmlValue(quote(value, '/>_= '))) else: xmlValue = '' if is_exception_on_eval: xmlCont = ' isErrorOnEval="True"' else: if resolver is not None: xmlCont = ' isContainer="True"' else: xmlCont = '' return ''.join((xml, xmlValue, xmlCont, additionalInXml, ' />\n')) if USE_PSYCO_OPTIMIZATION: try: import psyco varToXML = psyco.proxy(varToXML) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear() #don't keep the traceback -- clients don't want to see it
class PyDBFrame: '''This makes the tracing for a given frame, so, the trace_dispatch is used initially when we enter into a new context ('call') and then is reused for the entire context. ''' def __init__(self, args): #args = mainDebugger, filename, base, info, t, frame #yeap, much faster than putting in self and then getting it from self later on self._args = args[:-1] def setSuspend(self, *args, **kwargs): self._args[0].setSuspend(*args, **kwargs) def doWaitSuspend(self, *args, **kwargs): self._args[0].doWaitSuspend(*args, **kwargs) def trace_exception(self, frame, event, arg): if event == 'exception': mainDebugger = self._args[0] if not mainDebugger.break_on_caught: return None handle_exceptions = mainDebugger.handle_exceptions if handle_exceptions is not None and issubclass( arg[0], handle_exceptions): self.handle_exception(frame, event, arg) mainDebugger.SetTraceForFrameAndParents(frame) return self.trace_dispatch return self.trace_exception def handle_exception(self, frame, event, arg): thread = self._args[3] self.setSuspend(thread, CMD_STEP_INTO) self.doWaitSuspend(thread, frame, event, arg) def trace_dispatch(self, frame, event, arg): if event not in ('line', 'call', 'return'): if event == 'exception': mainDebugger = self._args[0] if mainDebugger.break_on_caught and issubclass( arg[0], mainDebugger.handle_exceptions): self.handle_exception(frame, event, arg) return self.trace_dispatch else: #I believe this can only happen in jython on some frontiers on jython and java code, which we don't want to trace. return None mainDebugger, filename, info, thread = self._args breakpoint = mainDebugger.breakpoints.get(filename) if info.pydev_state == STATE_RUN: #we can skip if: #- we have no stop marked #- we should make a step return/step over and we're not in the current frame can_skip = (info.pydev_step_cmd is None and info.pydev_step_stop is None)\ or (info.pydev_step_cmd in (CMD_STEP_RETURN, CMD_STEP_OVER) and info.pydev_step_stop is not frame) else: can_skip = False # Let's check to see if we are in a function that has a breakpoint. If we don't have a breakpoint, # we will return nothing for the next trace #also, after we hit a breakpoint and go to some other debugging state, we have to force the set trace anyway, #so, that's why the additional checks are there. if not breakpoint: if can_skip: if mainDebugger.break_on_caught: return self.trace_exception else: return None else: #checks the breakpoint to see if there is a context match in some function curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' for _b, condition, func_name in breakpoint.values( ): #jython does not support itervalues() #will match either global or some function if func_name in ('None', curr_func_name): break else: # if we had some break, it won't get here (so, that's a context that we want to skip) if can_skip: #print 'skipping', frame.f_lineno, info.pydev_state, info.pydev_step_stop, info.pydev_step_cmd if mainDebugger.break_on_caught: return self.trace_exception else: return None #We may have hit a breakpoint or we are already in step mode. Either way, let's check what we should do in this frame #print 'NOT skipped', frame.f_lineno, frame.f_code.co_name try: line = frame.f_lineno #return is not taken into account for breakpoint hit because we'd have a double-hit in this case #(one for the line and the other for the return). if event != 'return' and info.pydev_state != STATE_SUSPEND and breakpoint is not None \ and DictContains(breakpoint, line): #ok, hit breakpoint, now, we have to discover if it is a conditional breakpoint # lets do the conditional stuff here condition = breakpoint[line][1] if condition is not None: try: val = eval(condition, frame.f_globals, frame.f_locals) if not val: return self.trace_dispatch except: sys.stderr.write('Error while evaluating expression\n') traceback.print_exc() return self.trace_dispatch self.setSuspend(thread, CMD_SET_BREAK) # if thread has a suspend flag, we suspend with a busy wait if info.pydev_state == STATE_SUSPEND: self.doWaitSuspend(thread, frame, event, arg) return self.trace_dispatch except: traceback.print_exc() raise #step handling. We stop when we hit the right frame try: if info.pydev_step_cmd == CMD_STEP_INTO: stop = event in ('line', 'return') elif info.pydev_step_cmd == CMD_STEP_OVER: stop = info.pydev_step_stop is frame and event in ('line', 'return') elif info.pydev_step_cmd == CMD_STEP_RETURN: stop = event == 'return' and info.pydev_step_stop is frame elif info.pydev_step_cmd == CMD_RUN_TO_LINE or info.pydev_step_cmd == CMD_SET_NEXT_STATEMENT: stop = False if event == 'line' or event == 'exception': #Yes, we can only act on line events (weird hum?) #Note: This code is duplicated at pydevd.py #Acting on exception events after debugger breaks with exception curr_func_name = frame.f_code.co_name #global context is set with an empty name if curr_func_name in ('?', '<module>'): curr_func_name = '' if curr_func_name == info.pydev_func_name: line = info.pydev_next_line if frame.f_lineno == line: stop = True else: if frame.f_trace is None: frame.f_trace = self.trace_dispatch frame.f_lineno = line frame.f_trace = None stop = True else: stop = False if stop: #event is always == line or return at this point if event == 'line': self.setSuspend(thread, info.pydev_step_cmd) self.doWaitSuspend(thread, frame, event, arg) else: #return event back = frame.f_back if back is not None: #When we get to the pydevd run function, the debugging has actually finished for the main thread #(note that it can still go on for other threads, but for this one, we just make it finish) #So, just setting it to None should be OK base = basename(back.f_code.co_filename) if base == 'pydevd.py' and back.f_code.co_name == 'run': back = None elif base == 'pydevd_traceproperty.py': # We dont want to trace the return event of pydevd_traceproperty (custom property for debugging) #if we're in a return, we want it to appear to the user in the previous frame! return None if back is not None: self.setSuspend(thread, info.pydev_step_cmd) self.doWaitSuspend(thread, back, event, arg) else: #in jython we may not have a back frame info.pydev_step_stop = None info.pydev_step_cmd = None info.pydev_state = STATE_RUN except: traceback.print_exc() info.pydev_step_cmd = None #if we are quitting, let's stop the tracing retVal = None if not mainDebugger.quitting: retVal = self.trace_dispatch return retVal if USE_PSYCO_OPTIMIZATION: try: import psyco trace_dispatch = psyco.proxy(trace_dispatch) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear() #don't keep the traceback pass #ok, psyco not available
def f1(): return rect1.w * rect1.h def f2(a): rect1.w = a psyco.bind(f1) psyco.bind(f2) rect1.w = 6 rect1.h = 7 res = f1() assert res == 42 f2(4) res = f1() assert res == 28 f2(0.5) res = f1() assert res == 3.5 # ____________________________________________________________ if __name__ == '__main__': import time; print "break!"; time.sleep(1) #subprocess_test(10) #pcompact_test() #pcompact_creat('hel' + 'lo') #pcompact_modif('hel' + 'lo') #test_constant_obj() psyco.proxy(test_rect)() #psyco.proxy(test_special_attributes)() #psyco.proxy(test_data_descr)() psyco.dumpcodebuf()
def test_power_error_case(): def f(x, y): return x**y py.test.raises(ValueError, f, -4.5, 0.9) py.test.raises(ValueError, psyco.proxy(f), -4.5, 0.9)
def test_with_psyco(): yield psyco.proxy(test_rect) yield psyco.proxy(test_special_attributes) yield psyco.proxy(test_data_descr)
def test_power_error_case(): def f(x, y): return x ** y py.test.raises(ValueError, f, -4.5, 0.9) py.test.raises(ValueError, psyco.proxy(f), -4.5, 0.9)
def test_big_dict_constructor(): def f(x): return {1: 2, 3: 4, x: 6, 7: 8, 9: x, 'a': 'a', 'b': 'c', 'd': 'e', 'f': 'g'} assert psyco.proxy(f)(5) == f(5) assert psyco.proxy(f)('b') == f('b')
o['world':] o[1:10:'hello'] def listgetitem(): class X(list): def __getitem__(self, key): return key x = X(["Ok"]) print x["foobar"] for item in x: print item def negintpow(x): print x ** -2 if __name__ == '__main__': from test1 import go, print_results import time print "break!" time.sleep(0.5) #go(class_creation_1) #go(class_creation_2) #go(class_creation_3) #go(class_creation_4) #go(power_int) #go(power_int_long) #go(power_float) psyco.proxy(negintpow)(8) psyco.dumpcodebuf() print_results()
xmlValue = ' value="%s"' % (makeValidXmlValue(quote(value, '/>_= \t'))) else: xmlValue = '' if resolver is not None: xmlCont = ' isContainer="True"' else: xmlCont = '' return ''.join((xml, xmlValue, xmlCont, additionalInXml, ' />\n')) if USE_PSYCO_OPTIMIZATION: try: import psyco varToXML = psyco.proxy(varToXML) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear( ) #don't keep the traceback -- clients don't want to see it def frameVarsToXML(frame): """ dumps frame variables to XML <var name="var_name" scope="local" type="type" value="value"/> """ xml = "" keys = frame.f_locals.keys() if hasattr(keys, 'sort'): keys.sort() #Python 3.0 does not have it
if option == "Z": buffer = StringIO(zlib.decompress(buffer.read())) try: value = decoder[buffer.read(1)](buffer) except KeyError, e: raise DecodeError, "Type prefix not supported. (%s)" % e return value ## </decoding functions> ## try: import psyco dumps = psyco.proxy(dumps) loads = psyco.proxy(loads) except ImportError: pass if __name__ == "__main__": value = (u'\N{POUND SIGN} Testing unicode', { True: False }, [1, 2, 3, 4], ["simon"], ("python is", "cool"), "pi equals", 3.14, ("longs are ok", 912398102398102938102398109238019283012983019238019283019283)) data = dumps(value) print data x = loads(data) print x
buffer = StringIO(data) header = buffer.read(len(HEADER)) assert header == HEADER option = buffer.read(1) decompress = False if option == "Z": buffer = StringIO(zlib.decompress(buffer.read())) try: value = decoder[buffer.read(1)](buffer) except KeyError, e: raise DecodeError, "Type prefix not supported. (%s)" % e return value ## </decoding functions> ## try: import psyco dumps = psyco.proxy(dumps) loads = psyco.proxy(loads) except ImportError: pass if __name__ == "__main__": value = (u'\N{POUND SIGN} Testing unicode', {True:False},[1,2,3,4],["simon"],("python is","cool"), "pi equals",3.14,("longs are ok", 912398102398102938102398109238019283012983019238019283019283)) data = dumps(value) print data x = loads(data) print x
#always keep a reference to the topmost frame so that we're able to start tracing it (if it was untraced) #that's needed when a breakpoint is added in a current frame for a currently untraced context. #each new frame... dbFrame = additionalInfo.CreateDbFrame(self, filename, additionalInfo, t, frame) return dbFrame.trace_dispatch(frame, event, arg) except Exception, e: if not isinstance(e, SystemExit): traceback.print_exc() return None if USE_PSYCO_OPTIMIZATION: try: import psyco trace_dispatch = psyco.proxy(trace_dispatch) processNetCommand = psyco.proxy(processNetCommand) processInternalCommands = psyco.proxy(processInternalCommands) doWaitSuspend = psyco.proxy(doWaitSuspend) getInternalQueue = psyco.proxy(getInternalQueue) except ImportError: if hasattr(sys, 'exc_clear'): #jython does not have it sys.exc_clear() #don't keep the traceback (let's keep it clear for when we go to the point of executing client code) if not sys.platform.startswith("java"): print >> sys.stderr, "pydev debugger: warning: psyco not available for speedups (the debugger will still work correctly, but a bit slower)" def run(self, file, globals=None, locals=None): if globals is None: