# # Cython - Compilation-wide options and pragma declarations # cache_builtins = True # Perform lookups on builtin names only once embed_pos_in_docstring = False gcc_branch_hints = True pre_import = None docstrings = True # Decref global variables in this module on exit for garbage collection. # 0: None, 1+: interned objects, 2+: cdef globals, 3+: types objects # Mostly for reducing noise for Valgrind, only executes at process exit # (when all memory will be reclaimed anyways). generate_cleanup_code = False annotate = False # This will abort the compilation on the first error occured rather than trying # to keep going and printing further error messages. fast_fail = False # This will convert statements of the form "for i in range(...)" # to "for i from ..." when i is a cdef'd integer type, and the direction # (i.e. sign of step) can be determined. # WARNING: This may change the semantics if the range causes assignment to # i to overflow. Specifically, if this option is set, an error will be # raised before the loop is entered, wheras without this option the loop # will execute until an overflowing value is encountered. convert_range = True # Enable this to allow one to write your_module.foo = ... to overwrite the # definition if the cpdef function foo, at the cost of an extra dictionary # lookup on every call. # If this is 0 it simply creates a wrapper. lookup_module_cpdef = False # This will set local variables to None rather than NULL which may cause # surpress what would be an UnboundLocalError in pure Python but eliminates # checking for NULL on every use, and can decref rather than xdecref at the end. # WARNING: This is a work in progress, may currently segfault. init_local_none = True # Whether or not to embed the Python interpreter, for use in making a # standalone executable or calling from external libraries. # This will provide a method which initalizes the interpreter and # executes the body of this module. embed = None # Disables function redefinition, allowing all functions to be declared at # module creation time. For legacy code only, needed for some circular imports. disable_function_redefinition = False # Declare compiler directives directive_defaults = { 'boundscheck' : True, 'nonecheck' : False, 'embedsignature' : False, 'locals' : {}, 'auto_cpdef': False, 'cdivision': False, # was True before 0.12 'cdivision_warnings': False, 'always_allow_keywords': False, 'allow_none_for_extension_args': True, 'wraparound' : True, 'ccomplex' : False, # use C99/C++ for complex types and arith 'callspec' : "", 'final' : False, 'internal' : False, 'profile': False, 'infer_types': None, 'infer_types.verbose': False, 'autotestdict': True, 'autotestdict.cdef': False, 'autotestdict.all': False, 'language_level': 2, 'fast_getattr': False, # Undocumented until we come up with a better way to handle this everywhere. 'warn': None, 'warn.undeclared': False, # test support 'test_assert_path_exists' : [], 'test_fail_if_path_exists' : [], # experimental, subject to change 'binding': False, } # Override types possibilities above, if needed directive_types = { 'final' : bool, # final cdef classes and methods 'internal' : bool, # cdef class visibility in the module dict 'infer_types' : bool, # values can be True/None/False } for key, val in directive_defaults.items(): if key not in directive_types: directive_types[key] = type(val) directive_scopes = { # defaults to available everywhere # 'module', 'function', 'class', 'with statement' 'final' : ('cclass',), # add 'method' in the future 'internal' : ('cclass',), 'autotestdict' : ('module',), 'autotestdict.all' : ('module',), 'autotestdict.cdef' : ('module',), 'test_assert_path_exists' : ('function', 'class', 'cclass'), 'test_fail_if_path_exists' : ('function', 'class', 'cclass'), } def parse_directive_value(name, value, relaxed_bool=False): """ Parses value as an option value for the given name and returns the interpreted value. None is returned if the option does not exist. >>> print parse_directive_value('nonexisting', 'asdf asdfd') None >>> parse_directive_value('boundscheck', 'True') True >>> parse_directive_value('boundscheck', 'true') Traceback (most recent call last): ... ValueError: boundscheck directive must be set to True or False, got 'true' """ type = directive_types.get(name) if not type: return None orig_value = value if type is bool: value = str(value) if value == 'True': return True if value == 'False': return False if relaxed_bool: value = value.lower() if value in ("true", "yes"): return True elif value in ("false", "no"): return False raise ValueError("%s directive must be set to True or False, got '%s'" % ( name, orig_value)) elif type is int: try: return int(value) except ValueError: raise ValueError("%s directive must be set to an integer, got '%s'" % ( name, orig_value)) elif type is str: return str(value) else: assert False def parse_directive_list(s, relaxed_bool=False, ignore_unknown=False, current_settings=None): """ Parses a comma-separated list of pragma options. Whitespace is not considered. >>> parse_directive_list(' ') {} >>> (parse_directive_list('boundscheck=True') == ... {'boundscheck': True}) True >>> parse_directive_list(' asdf') Traceback (most recent call last): ... ValueError: Expected "=" in option "asdf" >>> parse_directive_list('boundscheck=hey') Traceback (most recent call last): ... ValueError: boundscheck directive must be set to True or False, got 'hey' >>> parse_directive_list('unknown=True') Traceback (most recent call last): ... ValueError: Unknown option: "unknown" """ if current_settings is None: result = {} else: result = current_settings for item in s.split(','): item = item.strip() if not item: continue if not '=' in item: raise ValueError('Expected "=" in option "%s"' % item) name, value = [ s.strip() for s in item.strip().split('=', 1) ] parsed_value = parse_directive_value(name, value, relaxed_bool=relaxed_bool) if parsed_value is None: if not ignore_unknown: raise ValueError('Unknown option: "%s"' % name) else: result[name] = parsed_value return result