Cython has moved to github.

cython

view Cython/Compiler/PyrexTypes.py @ 1118:f58bacff008d

long long indexing failed when sizeof(long long) < sizeof(Py_ssize_t)
author Robert Bradshaw <robertwb@math.washington.edu>
date Tue Aug 26 00:06:52 2008 -0700 (3 years ago)
parents 71efafd69bad
children 3cd7a93fd553 64f0185097a9
line source
1 #
2 # Pyrex - Types
3 #
5 import StringEncoding
6 import Naming
7 import copy
10 class BaseType:
11 #
12 # Base class for all Pyrex types including pseudo-types.
14 def cast_code(self, expr_code):
15 return "((%s)%s)" % (self.declaration_code(""), expr_code)
17 def base_declaration_code(self, base_code, entity_code):
18 if entity_code:
19 return "%s %s" % (base_code, entity_code)
20 else:
21 return base_code
24 class PyrexType(BaseType):
25 #
26 # Base class for all Pyrex types.
27 #
28 # is_pyobject boolean Is a Python object type
29 # is_extension_type boolean Is a Python extension type
30 # is_numeric boolean Is a C numeric type
31 # is_int boolean Is a C integer type
32 # is_longlong boolean Is a long long or unsigned long long.
33 # is_float boolean Is a C floating point type
34 # is_void boolean Is the C void type
35 # is_array boolean Is a C array type
36 # is_ptr boolean Is a C pointer type
37 # is_null_ptr boolean Is the type of NULL
38 # is_cfunction boolean Is a C function type
39 # is_struct_or_union boolean Is a C struct or union type
40 # is_enum boolean Is a C enum type
41 # is_typedef boolean Is a typedef type
42 # is_string boolean Is a C char * type
43 # is_unicode boolean Is a UTF-8 encoded C char * type
44 # is_returncode boolean Is used only to signal exceptions
45 # is_error boolean Is the dummy error type
46 # is_buffer boolean Is buffer access type
47 # has_attributes boolean Has C dot-selectable attributes
48 # default_value string Initial value
49 # parsetuple_format string Format char for PyArg_ParseTuple
50 # pymemberdef_typecode string Type code for PyMemberDef struct
51 # typestring string String char defining the type (see Python struct module)
52 #
53 # declaration_code(entity_code,
54 # for_display = 0, dll_linkage = None, pyrex = 0)
55 # Returns a code fragment for the declaration of an entity
56 # of this type, given a code fragment for the entity.
57 # * If for_display, this is for reading by a human in an error
58 # message; otherwise it must be valid C code.
59 # * If dll_linkage is not None, it must be 'DL_EXPORT' or
60 # 'DL_IMPORT', and will be added to the base type part of
61 # the declaration.
62 # * If pyrex = 1, this is for use in a 'cdef extern'
63 # statement of a Pyrex include file.
64 #
65 # assignable_from(src_type)
66 # Tests whether a variable of this type can be
67 # assigned a value of type src_type.
68 #
69 # same_as(other_type)
70 # Tests whether this type represents the same type
71 # as other_type.
72 #
73 # as_argument_type():
74 # Coerces array type into pointer type for use as
75 # a formal argument type.
76 #
78 is_pyobject = 0
79 is_extension_type = 0
80 is_builtin_type = 0
81 is_numeric = 0
82 is_int = 0
83 is_longlong = 0
84 is_float = 0
85 is_void = 0
86 is_array = 0
87 is_ptr = 0
88 is_null_ptr = 0
89 is_cfunction = 0
90 is_struct_or_union = 0
91 is_enum = 0
92 is_typedef = 0
93 is_string = 0
94 is_unicode = 0
95 is_returncode = 0
96 is_error = 0
97 is_buffer = 0
98 has_attributes = 0
99 default_value = ""
100 parsetuple_format = ""
101 pymemberdef_typecode = None
103 def resolve(self):
104 # If a typedef, returns the base type.
105 return self
107 def literal_code(self, value):
108 # Returns a C code fragment representing a literal
109 # value of this type.
110 return str(value)
112 def __str__(self):
113 return self.declaration_code("", for_display = 1).strip()
115 def same_as(self, other_type, **kwds):
116 return self.same_as_resolved_type(other_type.resolve(), **kwds)
118 def same_as_resolved_type(self, other_type):
119 return self == other_type or other_type is error_type
121 def subtype_of(self, other_type):
122 return self.subtype_of_resolved_type(other_type.resolve())
124 def subtype_of_resolved_type(self, other_type):
125 return self.same_as(other_type)
127 def assignable_from(self, src_type):
128 return self.assignable_from_resolved_type(src_type.resolve())
130 def assignable_from_resolved_type(self, src_type):
131 return self.same_as(src_type)
133 def as_argument_type(self):
134 return self
136 def is_complete(self):
137 # A type is incomplete if it is an unsized array,
138 # a struct whose attributes are not defined, etc.
139 return 1
142 class CTypedefType(BaseType):
143 #
144 # Pseudo-type defined with a ctypedef statement in a
145 # 'cdef extern from' block. Delegates most attribute
146 # lookups to the base type. ANYTHING NOT DEFINED
147 # HERE IS DELEGATED!
148 #
149 # qualified_name string
150 # typedef_cname string
151 # typedef_base_type PyrexType
153 is_typedef = 1
154 typestring = None # Because typedefs are not known exactly
156 def __init__(self, cname, base_type):
157 self.typedef_cname = cname
158 self.typedef_base_type = base_type
160 def resolve(self):
161 return self.typedef_base_type.resolve()
163 def declaration_code(self, entity_code,
164 for_display = 0, dll_linkage = None, pyrex = 0):
165 name = self.declaration_name(for_display, pyrex)
166 return self.base_declaration_code(name, entity_code)
168 def declaration_name(self, for_display = 0, pyrex = 0):
169 if pyrex or for_display:
170 return self.qualified_name
171 else:
172 return self.typedef_cname
174 def as_argument_type(self):
175 return self
177 def cast_code(self, expr_code):
178 # If self is really an array (rather than pointer), we can't cast.
179 # For example, the gmp mpz_t.
180 if self.typedef_base_type.is_ptr:
181 return self.typedef_base_type.cast_code(expr_code)
182 else:
183 return BaseType.cast_code(self, expr_code)
185 def __repr__(self):
186 return "<CTypedefType %s>" % self.typedef_cname
188 def __str__(self):
189 return self.declaration_name(for_display = 1)
191 def __getattr__(self, name):
192 return getattr(self.typedef_base_type, name)
194 class BufferType(BaseType):
195 #
196 # Delegates most attribute
197 # lookups to the base type. ANYTHING NOT DEFINED
198 # HERE IS DELEGATED!
200 # dtype PyrexType
201 # ndim int
202 # mode str
203 # is_buffer boolean
204 # writable boolean
206 is_buffer = 1
207 writable = True
208 def __init__(self, base, dtype, ndim, mode):
209 self.base = base
210 self.dtype = dtype
211 self.ndim = ndim
212 self.buffer_ptr_type = CPtrType(dtype)
213 self.mode = mode
215 def as_argument_type(self):
216 return self
218 def __getattr__(self, name):
219 return getattr(self.base, name)
221 def __repr__(self):
222 return "<BufferType %r>" % self.base
225 class PyObjectType(PyrexType):
226 #
227 # Base class for all Python object types (reference-counted).
228 #
229 # buffer_defaults dict or None Default options for bu
231 is_pyobject = 1
232 default_value = "0"
233 parsetuple_format = "O"
234 pymemberdef_typecode = "T_OBJECT"
235 buffer_defaults = None
236 typestring = "O"
238 def __str__(self):
239 return "Python object"
241 def __repr__(self):
242 return "<PyObjectType>"
244 def assignable_from(self, src_type):
245 return 1 # Conversion will be attempted
247 def declaration_code(self, entity_code,
248 for_display = 0, dll_linkage = None, pyrex = 0):
249 if pyrex or for_display:
250 return self.base_declaration_code("object", entity_code)
251 else:
252 return "%s *%s" % (public_decl("PyObject", dll_linkage), entity_code)
255 class BuiltinObjectType(PyObjectType):
257 is_builtin_type = 1
258 has_attributes = 1
259 base_type = None
260 module_name = '__builtin__'
262 def __init__(self, name, cname):
263 self.name = name
264 self.cname = cname
265 self.typeptr_cname = "&" + cname
267 def set_scope(self, scope):
268 self.scope = scope
269 if scope:
270 scope.parent_type = self
272 def __str__(self):
273 return "%s object" % self.name
275 def __repr__(self):
276 return "<%s>"% self.cname
278 def assignable_from(self, src_type):
280 if isinstance(src_type, BuiltinObjectType):
281 return src_type.name == self.name
282 else:
283 return not src_type.is_extension_type
285 def typeobj_is_available(self):
286 return True
288 def attributes_known(self):
289 return True
291 def subtype_of(self, type):
292 return type.is_pyobject and self.assignable_from(type)
294 def type_test_code(self, arg):
295 return 'likely(Py%s_CheckExact(%s)) || (%s) == Py_None || (PyErr_Format(PyExc_TypeError, "Expected %s, got %%s", Py_TYPE(%s)->tp_name), 0)' % (self.name[0].upper() + self.name[1:], arg, arg, self.name, arg)
297 def declaration_code(self, entity_code,
298 for_display = 0, dll_linkage = None, pyrex = 0):
299 if pyrex or for_display:
300 return self.base_declaration_code(self.name, entity_code)
301 else:
302 return "%s *%s" % (public_decl("PyObject", dll_linkage), entity_code)
305 class PyExtensionType(PyObjectType):
306 #
307 # A Python extension type.
308 #
309 # name string
310 # scope CClassScope Attribute namespace
311 # visibility string
312 # typedef_flag boolean
313 # base_type PyExtensionType or None
314 # module_name string or None Qualified name of defining module
315 # objstruct_cname string Name of PyObject struct
316 # typeobj_cname string or None C code fragment referring to type object
317 # typeptr_cname string or None Name of pointer to external type object
318 # vtabslot_cname string Name of C method table member
319 # vtabstruct_cname string Name of C method table struct
320 # vtabptr_cname string Name of pointer to C method table
321 # vtable_cname string Name of C method table definition
323 is_extension_type = 1
324 has_attributes = 1
326 def __init__(self, name, typedef_flag, base_type):
327 self.name = name
328 self.scope = None
329 self.typedef_flag = typedef_flag
330 self.base_type = base_type
331 self.module_name = None
332 self.objstruct_cname = None
333 self.typeobj_cname = None
334 self.typeptr_cname = None
335 self.vtabslot_cname = None
336 self.vtabstruct_cname = None
337 self.vtabptr_cname = None
338 self.vtable_cname = None
340 def set_scope(self, scope):
341 self.scope = scope
342 if scope:
343 scope.parent_type = self
345 def subtype_of_resolved_type(self, other_type):
346 if other_type.is_extension_type:
347 return self is other_type or (
348 self.base_type and self.base_type.subtype_of(other_type))
349 else:
350 return other_type is py_object_type
352 def typeobj_is_available(self):
353 # Do we have a pointer to the type object?
354 return self.typeptr_cname
356 def typeobj_is_imported(self):
357 # If we don't know the C name of the type object but we do
358 # know which module it's defined in, it will be imported.
359 return self.typeobj_cname is None and self.module_name is not None
361 def declaration_code(self, entity_code,
362 for_display = 0, dll_linkage = None, pyrex = 0, deref = 0):
363 if pyrex or for_display:
364 return self.base_declaration_code(self.name, entity_code)
365 else:
366 if self.typedef_flag:
367 base_format = "%s"
368 else:
369 base_format = "struct %s"
370 base = public_decl(base_format % self.objstruct_cname, dll_linkage)
371 if deref:
372 return "%s %s" % (base, entity_code)
373 else:
374 return "%s *%s" % (base, entity_code)
376 def type_test_code(self, py_arg):
377 return "__Pyx_TypeTest(%s, %s)" % (py_arg, self.typeptr_cname)
379 def attributes_known(self):
380 return self.scope is not None
382 def __str__(self):
383 return self.name
385 def __repr__(self):
386 return "<PyExtensionType %s%s>" % (self.scope.class_name,
387 ("", " typedef")[self.typedef_flag])
390 class CType(PyrexType):
391 #
392 # Base class for all C types (non-reference-counted).
393 #
394 # to_py_function string C function for converting to Python object
395 # from_py_function string C function for constructing from Python object
396 #
398 to_py_function = None
399 from_py_function = None
400 exception_value = None
401 exception_check = 1
403 def error_condition(self, result_code):
404 conds = []
405 if self.is_string:
406 conds.append("(!%s)" % result_code)
407 elif self.exception_value is not None:
408 conds.append("(%s == (%s)%s)" % (result_code, self.sign_and_name(), self.exception_value))
409 if self.exception_check:
410 conds.append("PyErr_Occurred()")
411 if len(conds) > 0:
412 return " && ".join(conds)
413 else:
414 return 0
417 class CVoidType(CType):
418 is_void = 1
420 def __repr__(self):
421 return "<CVoidType>"
423 def declaration_code(self, entity_code,
424 for_display = 0, dll_linkage = None, pyrex = 0):
425 base = public_decl("void", dll_linkage)
426 return self.base_declaration_code(base, entity_code)
428 def is_complete(self):
429 return 0
432 class CNumericType(CType):
433 #
434 # Base class for all C numeric types.
435 #
436 # rank integer Relative size
437 # signed integer 0 = unsigned, 1 = unspecified, 2 = explicitly signed
438 #
440 is_numeric = 1
441 default_value = "0"
443 parsetuple_formats = ( # rank -> format
444 "BHIkK????", # unsigned
445 "bhilL?fd?", # assumed signed
446 "bhilL?fd?", # explicitly signed
447 )
449 sign_words = ("unsigned ", "", "signed ")
451 def __init__(self, rank, signed = 1, pymemberdef_typecode = None, typestring = None):
452 self.rank = rank
453 self.signed = signed
454 self.typestring = typestring
455 ptf = self.parsetuple_formats[signed][rank]
456 if ptf == '?':
457 ptf = None
458 self.parsetuple_format = ptf
459 self.pymemberdef_typecode = pymemberdef_typecode
461 def sign_and_name(self):
462 s = self.sign_words[self.signed]
463 n = rank_to_type_name[self.rank]
464 return s + n
466 def __repr__(self):
467 return "<CNumericType %s>" % self.sign_and_name()
469 def declaration_code(self, entity_code,
470 for_display = 0, dll_linkage = None, pyrex = 0):
471 base = public_decl(self.sign_and_name(), dll_linkage)
472 return self.base_declaration_code(base, entity_code)
475 int_conversion_list = {}
476 type_conversion_functions = ""
477 type_conversion_predeclarations = ""
479 class CIntType(CNumericType):
481 is_int = 1
482 typedef_flag = 0
483 to_py_function = "PyInt_FromLong"
484 from_py_function = "__pyx_PyInt_AsLong"
485 exception_value = -1
487 def __init__(self, rank, signed, pymemberdef_typecode = None, is_returncode = 0,
488 typestring=None):
489 CNumericType.__init__(self, rank, signed, pymemberdef_typecode, typestring=typestring)
490 self.is_returncode = is_returncode
491 if self.from_py_function == '__pyx_PyInt_AsLong':
492 self.from_py_function = self.get_type_conversion()
494 def get_type_conversion(self):
495 # error on overflow
496 c_type = self.sign_and_name()
497 c_name = c_type.replace(' ', '_');
498 func_name = "__pyx_PyInt_%s" % c_name;
499 if not int_conversion_list.has_key(func_name):
500 # no env to add utility code to
501 global type_conversion_predeclarations, type_conversion_functions
502 if self.signed:
503 neg_test = ""
504 else:
505 neg_test = " || (long_val < 0)"
506 type_conversion_predeclarations += """
507 static INLINE %(c_type)s %(func_name)s(PyObject* x);""" % {'c_type': c_type, 'c_name': c_name, 'func_name': func_name }
508 type_conversion_functions += """
509 static INLINE %(c_type)s %(func_name)s(PyObject* x) {
510 if (sizeof(%(c_type)s) < sizeof(long)) {
511 long long_val = __pyx_PyInt_AsLong(x);
512 %(c_type)s val = (%(c_type)s)long_val;
513 if (unlikely((val != long_val) %(neg_test)s)) {
514 PyErr_SetString(PyExc_OverflowError, "value too large to convert to %(c_type)s");
515 return (%(c_type)s)-1;
516 }
517 return val;
518 }
519 else {
520 return __pyx_PyInt_AsLong(x);
521 }
522 }
523 """ % {'c_type': c_type, 'c_name': c_name, 'func_name': func_name, 'neg_test': neg_test }
524 int_conversion_list[func_name] = True
525 return func_name
527 def assignable_from_resolved_type(self, src_type):
528 return src_type.is_int or src_type.is_enum or src_type is error_type
531 class CBIntType(CIntType):
533 to_py_function = "__Pyx_PyBool_FromLong"
534 from_py_function = "__Pyx_PyObject_IsTrue"
535 exception_check = 0
538 class CAnonEnumType(CIntType):
540 is_enum = 1
543 class CUIntType(CIntType):
545 to_py_function = "PyLong_FromUnsignedLong"
546 from_py_function = "PyInt_AsUnsignedLongMask"
547 exception_value = -1
550 class CULongType(CUIntType):
552 to_py_function = "PyLong_FromUnsignedLong"
553 from_py_function = "PyInt_AsUnsignedLongMask"
556 class CLongLongType(CUIntType):
558 is_longlong = 1
559 to_py_function = "PyLong_FromLongLong"
560 from_py_function = "__pyx_PyInt_AsLongLong"
563 class CULongLongType(CUIntType):
565 is_longlong = 1
566 to_py_function = "PyLong_FromUnsignedLongLong"
567 from_py_function = "__pyx_PyInt_AsUnsignedLongLong"
570 class CPySSizeTType(CIntType):
572 to_py_function = "PyInt_FromSsize_t"
573 from_py_function = "__pyx_PyIndex_AsSsize_t"
576 class CFloatType(CNumericType):
578 is_float = 1
579 to_py_function = "PyFloat_FromDouble"
580 from_py_function = "__pyx_PyFloat_AsDouble"
582 def __init__(self, rank, pymemberdef_typecode = None, typestring=None):
583 CNumericType.__init__(self, rank, 1, pymemberdef_typecode, typestring = typestring)
585 def assignable_from_resolved_type(self, src_type):
586 return src_type.is_numeric or src_type is error_type
589 class CArrayType(CType):
590 # base_type CType Element type
591 # size integer or None Number of elements
593 is_array = 1
595 def __init__(self, base_type, size):
596 self.base_type = base_type
597 self.size = size
598 if base_type is c_char_type:
599 self.is_string = 1
601 def __repr__(self):
602 return "<CArrayType %s %s>" % (self.size, repr(self.base_type))
604 def same_as_resolved_type(self, other_type):
605 return ((other_type.is_array and
606 self.base_type.same_as(other_type.base_type))
607 or other_type is error_type)
609 def assignable_from_resolved_type(self, src_type):
610 # Can't assign to a variable of an array type
611 return 0
613 def element_ptr_type(self):
614 return c_ptr_type(self.base_type)
616 def declaration_code(self, entity_code,
617 for_display = 0, dll_linkage = None, pyrex = 0):
618 if self.size is not None:
619 dimension_code = self.size
620 else:
621 dimension_code = ""
622 if entity_code.startswith("*"):
623 entity_code = "(%s)" % entity_code
624 return self.base_type.declaration_code(
625 "%s[%s]" % (entity_code, dimension_code),
626 for_display, dll_linkage, pyrex)
628 def as_argument_type(self):
629 return c_ptr_type(self.base_type)
631 def is_complete(self):
632 return self.size is not None
635 class CPtrType(CType):
636 # base_type CType Referenced type
638 is_ptr = 1
639 default_value = "0"
641 def __init__(self, base_type):
642 self.base_type = base_type
644 def __repr__(self):
645 return "<CPtrType %s>" % repr(self.base_type)
647 def same_as_resolved_type(self, other_type):
648 return ((other_type.is_ptr and
649 self.base_type.same_as(other_type.base_type))
650 or other_type is error_type)
652 def declaration_code(self, entity_code,
653 for_display = 0, dll_linkage = None, pyrex = 0):
654 #print "CPtrType.declaration_code: pointer to", self.base_type ###
655 return self.base_type.declaration_code(
656 "*%s" % entity_code,
657 for_display, dll_linkage, pyrex)
659 def assignable_from_resolved_type(self, other_type):
660 if other_type is error_type:
661 return 1
662 if other_type.is_null_ptr:
663 return 1
664 if self.base_type.is_cfunction:
665 if other_type.is_ptr:
666 other_type = other_type.base_type.resolve()
667 if other_type.is_cfunction:
668 return self.base_type.pointer_assignable_from_resolved_type(other_type)
669 else:
670 return 0
671 if other_type.is_array or other_type.is_ptr:
672 return self.base_type.is_void or self.base_type.same_as(other_type.base_type)
673 return 0
676 class CNullPtrType(CPtrType):
678 is_null_ptr = 1
681 class CFuncType(CType):
682 # return_type CType
683 # args [CFuncTypeArg]
684 # has_varargs boolean
685 # exception_value string
686 # exception_check boolean True if PyErr_Occurred check needed
687 # calling_convention string Function calling convention
688 # nogil boolean Can be called without gil
689 # with_gil boolean Acquire gil around function body
691 is_cfunction = 1
692 original_sig = None
694 def __init__(self, return_type, args, has_varargs = 0,
695 exception_value = None, exception_check = 0, calling_convention = "",
696 nogil = 0, with_gil = 0, is_overridable = 0, optional_arg_count = 0):
697 self.return_type = return_type
698 self.args = args
699 self.has_varargs = has_varargs
700 self.optional_arg_count = optional_arg_count
701 self.exception_value = exception_value
702 self.exception_check = exception_check
703 self.calling_convention = calling_convention
704 self.nogil = nogil
705 self.with_gil = with_gil
706 self.is_overridable = is_overridable
708 def __repr__(self):
709 arg_reprs = map(repr, self.args)
710 if self.has_varargs:
711 arg_reprs.append("...")
712 return "<CFuncType %s %s[%s]>" % (
713 repr(self.return_type),
714 self.calling_convention_prefix(),
715 ",".join(arg_reprs))
717 def calling_convention_prefix(self):
718 cc = self.calling_convention
719 if cc:
720 return cc + " "
721 else:
722 return ""
724 def same_c_signature_as(self, other_type, as_cmethod = 0):
725 return self.same_c_signature_as_resolved_type(
726 other_type.resolve(), as_cmethod)
728 def same_c_signature_as_resolved_type(self, other_type, as_cmethod = 0):
729 #print "CFuncType.same_c_signature_as_resolved_type:", \
730 # self, other_type, "as_cmethod =", as_cmethod ###
731 if other_type is error_type:
732 return 1
733 if not other_type.is_cfunction:
734 return 0
735 if not self.is_overridable and other_type.is_overridable:
736 return 0
737 nargs = len(self.args)
738 if nargs != len(other_type.args):
739 return 0
740 # When comparing C method signatures, the first argument
741 # is exempt from compatibility checking (the proper check
742 # is performed elsewhere).
743 for i in range(as_cmethod, nargs):
744 if not self.args[i].type.same_as(
745 other_type.args[i].type):
746 return 0
747 if self.has_varargs != other_type.has_varargs:
748 return 0
749 if self.optional_arg_count != other_type.optional_arg_count:
750 return 0
751 if not self.return_type.same_as(other_type.return_type):
752 return 0
753 if not self.same_calling_convention_as(other_type):
754 return 0
755 return 1
757 def compatible_signature_with(self, other_type, as_cmethod = 0):
758 return self.compatible_signature_with_resolved_type(other_type.resolve(), as_cmethod)
760 def compatible_signature_with_resolved_type(self, other_type, as_cmethod):
761 #print "CFuncType.same_c_signature_as_resolved_type:", \
762 # self, other_type, "as_cmethod =", as_cmethod ###
763 if other_type is error_type:
764 return 1
765 if not other_type.is_cfunction:
766 return 0
767 if not self.is_overridable and other_type.is_overridable:
768 return 0
769 nargs = len(self.args)
770 if nargs - self.optional_arg_count != len(other_type.args) - other_type.optional_arg_count:
771 return 0
772 if self.optional_arg_count < other_type.optional_arg_count:
773 return 0
774 # When comparing C method signatures, the first argument
775 # is exempt from compatibility checking (the proper check
776 # is performed elsewhere).
777 for i in range(as_cmethod, len(other_type.args)):
778 if not self.args[i].type.same_as(
779 other_type.args[i].type):
780 return 0
781 if self.has_varargs != other_type.has_varargs:
782 return 0
783 if not self.return_type.subtype_of_resolved_type(other_type.return_type):
784 return 0
785 if not self.same_calling_convention_as(other_type):
786 return 0
787 if self.nogil != other_type.nogil:
788 return 0
789 self.original_sig = other_type.original_sig or other_type
790 if as_cmethod:
791 self.args[0] = other_type.args[0]
792 return 1
795 def narrower_c_signature_than(self, other_type, as_cmethod = 0):
796 return self.narrower_c_signature_than_resolved_type(other_type.resolve(), as_cmethod)
798 def narrower_c_signature_than_resolved_type(self, other_type, as_cmethod):
799 if other_type is error_type:
800 return 1
801 if not other_type.is_cfunction:
802 return 0
803 nargs = len(self.args)
804 if nargs != len(other_type.args):
805 return 0
806 for i in range(as_cmethod, nargs):
807 if not self.args[i].type.subtype_of_resolved_type(other_type.args[i].type):
808 return 0
809 else:
810 self.args[i].needs_type_test = other_type.args[i].needs_type_test \
811 or not self.args[i].type.same_as(other_type.args[i].type)
812 if self.has_varargs != other_type.has_varargs:
813 return 0
814 if self.optional_arg_count != other_type.optional_arg_count:
815 return 0
816 if not self.return_type.subtype_of_resolved_type(other_type.return_type):
817 return 0
818 return 1
820 def same_calling_convention_as(self, other):
821 sc1 = self.calling_convention == '__stdcall'
822 sc2 = other.calling_convention == '__stdcall'
823 return sc1 == sc2
825 def same_exception_signature_as(self, other_type):
826 return self.same_exception_signature_as_resolved_type(
827 other_type.resolve())
829 def same_exception_signature_as_resolved_type(self, other_type):
830 return self.exception_value == other_type.exception_value \
831 and self.exception_check == other_type.exception_check
833 def same_as_resolved_type(self, other_type, as_cmethod = 0):
834 return self.same_c_signature_as_resolved_type(other_type, as_cmethod) \
835 and self.same_exception_signature_as_resolved_type(other_type) \
836 and self.nogil == other_type.nogil
838 def pointer_assignable_from_resolved_type(self, other_type):
839 return self.same_c_signature_as_resolved_type(other_type) \
840 and self.same_exception_signature_as_resolved_type(other_type) \
841 and not (self.nogil and not other_type.nogil)
843 def declaration_code(self, entity_code,
844 for_display = 0, dll_linkage = None, pyrex = 0):
845 arg_decl_list = []
846 for arg in self.args[:len(self.args)-self.optional_arg_count]:
847 arg_decl_list.append(
848 arg.type.declaration_code("", for_display, pyrex = pyrex))
849 if self.optional_arg_count:
850 arg_decl_list.append(self.op_arg_struct.declaration_code(Naming.optional_args_cname))
851 if self.has_varargs:
852 arg_decl_list.append("...")
853 arg_decl_code = ", ".join(arg_decl_list)
854 if not arg_decl_code and not pyrex:
855 arg_decl_code = "void"
856 trailer = ""
857 if (pyrex or for_display) and not self.return_type.is_pyobject:
858 if self.exception_value and self.exception_check:
859 trailer = " except? %s" % self.exception_value
860 elif self.exception_value:
861 trailer = " except %s" % self.exception_value
862 elif self.exception_check == '+':
863 trailer = " except +"
864 else:
865 " except *" # ignored
866 if self.nogil:
867 trailer += " nogil"
868 cc = self.calling_convention_prefix()
869 if (not entity_code and cc) or entity_code.startswith("*"):
870 entity_code = "(%s%s)" % (cc, entity_code)
871 cc = ""
872 return self.return_type.declaration_code(
873 "%s%s(%s)%s" % (cc, entity_code, arg_decl_code, trailer),
874 for_display, dll_linkage, pyrex)
876 def function_header_code(self, func_name, arg_code):
877 return "%s%s(%s)" % (self.calling_convention_prefix(),
878 func_name, arg_code)
880 def signature_string(self):
881 s = self.declaration_code("")
882 return s
885 class CFuncTypeArg:
886 # name string
887 # cname string
888 # type PyrexType
889 # pos source file position
891 def __init__(self, name, type, pos, cname=None):
892 self.name = name
893 if cname is not None:
894 self.cname = cname
895 else:
896 self.cname = Naming.var_prefix + name
897 self.type = type
898 self.pos = pos
899 self.not_none = False
900 self.needs_type_test = False # TODO: should these defaults be set in analyse_types()?
902 def __repr__(self):
903 return "%s:%s" % (self.name, repr(self.type))
905 def declaration_code(self, for_display = 0):
906 return self.type.declaration_code(self.cname, for_display)
909 class CStructOrUnionType(CType):
910 # name string
911 # cname string
912 # kind string "struct" or "union"
913 # scope StructOrUnionScope, or None if incomplete
914 # typedef_flag boolean
916 is_struct_or_union = 1
917 has_attributes = 1
919 def __init__(self, name, kind, scope, typedef_flag, cname):
920 self.name = name
921 self.cname = cname
922 self.kind = kind
923 self.scope = scope
924 self.typedef_flag = typedef_flag
926 def __repr__(self):
927 return "<CStructOrUnionType %s %s%s>" % (self.name, self.cname,
928 ("", " typedef")[self.typedef_flag])
930 def declaration_code(self, entity_code,
931 for_display = 0, dll_linkage = None, pyrex = 0):
932 if pyrex:
933 return self.base_declaration_code(self.name, entity_code)
934 else:
935 if for_display:
936 base = self.name
937 elif self.typedef_flag:
938 base = self.cname
939 else:
940 base = "%s %s" % (self.kind, self.cname)
941 return self.base_declaration_code(public_decl(base, dll_linkage), entity_code)
943 def __cmp__(self, other):
944 try:
945 if self.name == other.name:
946 return 0
947 else:
948 return 1
949 except AttributeError:
950 return 1
952 def is_complete(self):
953 return self.scope is not None
955 def attributes_known(self):
956 return self.is_complete()
959 class CEnumType(CType):
960 # name string
961 # cname string or None
962 # typedef_flag boolean
964 is_enum = 1
965 signed = 1
966 rank = -1 # Ranks below any integer type
967 to_py_function = "PyInt_FromLong"
968 from_py_function = "PyInt_AsLong"
970 def __init__(self, name, cname, typedef_flag):
971 self.name = name
972 self.cname = cname
973 self.values = []
974 self.typedef_flag = typedef_flag
976 def __str__(self):
977 return self.name
979 def __repr__(self):
980 return "<CEnumType %s %s%s>" % (self.name, self.cname,
981 ("", " typedef")[self.typedef_flag])
983 def declaration_code(self, entity_code,
984 for_display = 0, dll_linkage = None, pyrex = 0):
985 if pyrex:
986 return self.base_declaration_code(self.cname, entity_code)
987 else:
988 if self.typedef_flag:
989 base = self.cname
990 else:
991 base = "enum %s" % self.cname
992 return self.base_declaration_code(public_decl(base, dll_linkage), entity_code)
995 class CStringType:
996 # Mixin class for C string types.
998 is_string = 1
999 is_unicode = 0
1001 to_py_function = "__Pyx_PyBytes_FromString"
1002 from_py_function = "__Pyx_PyBytes_AsString"
1003 exception_value = "NULL"
1005 def literal_code(self, value):
1006 assert isinstance(value, str)
1007 return '"%s"' % StringEncoding.escape_byte_string(value)
1010 class CUTF8CharArrayType(CStringType, CArrayType):
1011 # C 'char []' type.
1013 parsetuple_format = "s"
1014 pymemberdef_typecode = "T_STRING_INPLACE"
1015 is_unicode = 1
1017 to_py_function = "PyUnicode_DecodeUTF8"
1018 exception_value = "NULL"
1020 def __init__(self, size):
1021 CArrayType.__init__(self, c_char_type, size)
1023 class CCharArrayType(CStringType, CArrayType):
1024 # C 'char []' type.
1026 parsetuple_format = "s"
1027 pymemberdef_typecode = "T_STRING_INPLACE"
1029 def __init__(self, size):
1030 CArrayType.__init__(self, c_char_type, size)
1033 class CCharPtrType(CStringType, CPtrType):
1034 # C 'char *' type.
1036 parsetuple_format = "s"
1037 pymemberdef_typecode = "T_STRING"
1039 def __init__(self):
1040 CPtrType.__init__(self, c_char_type)
1043 class ErrorType(PyrexType):
1044 # Used to prevent propagation of error messages.
1046 is_error = 1
1047 exception_value = "0"
1048 exception_check = 0
1049 to_py_function = "dummy"
1050 from_py_function = "dummy"
1051 typestring = None
1053 def declaration_code(self, entity_code,
1054 for_display = 0, dll_linkage = None, pyrex = 0):
1055 return "<error>"
1057 def same_as_resolved_type(self, other_type):
1058 return 1
1060 def error_condition(self, result_code):
1061 return "dummy"
1064 rank_to_type_name = (
1065 "char", # 0
1066 "short", # 1
1067 "int", # 2
1068 "long", # 3
1069 "PY_LONG_LONG", # 4
1070 "Py_ssize_t", # 5
1071 "float", # 6
1072 "double", # 7
1073 "long double", # 8
1076 py_object_type = PyObjectType()
1078 c_void_type = CVoidType()
1079 c_void_ptr_type = CPtrType(c_void_type)
1080 c_void_ptr_ptr_type = CPtrType(c_void_ptr_type)
1082 c_uchar_type = CIntType(0, 0, "T_UBYTE", typestring="B")
1083 c_ushort_type = CIntType(1, 0, "T_USHORT", typestring="H")
1084 c_uint_type = CUIntType(2, 0, "T_UINT", typestring="I")
1085 c_ulong_type = CULongType(3, 0, "T_ULONG", typestring="L")
1086 c_ulonglong_type = CULongLongType(4, 0, "T_ULONGLONG", typestring="Q")
1088 c_char_type = CIntType(0, 1, "T_CHAR", typestring="b")
1089 c_short_type = CIntType(1, 1, "T_SHORT", typestring="h")
1090 c_int_type = CIntType(2, 1, "T_INT", typestring="i")
1091 c_long_type = CIntType(3, 1, "T_LONG", typestring="l")
1092 c_longlong_type = CLongLongType(4, 1, "T_LONGLONG", typestring="q")
1093 c_py_ssize_t_type = CPySSizeTType(5, 1)
1094 c_bint_type = CBIntType(2, 1, "T_INT", typestring="i")
1096 c_schar_type = CIntType(0, 2, "T_CHAR", typestring="b")
1097 c_sshort_type = CIntType(1, 2, "T_SHORT", typestring="h")
1098 c_sint_type = CIntType(2, 2, "T_INT", typestring="i")
1099 c_slong_type = CIntType(3, 2, "T_LONG", typestring="l")
1100 c_slonglong_type = CLongLongType(4, 2, "T_LONGLONG", typestring="q")
1102 c_float_type = CFloatType(6, "T_FLOAT", typestring="f")
1103 c_double_type = CFloatType(7, "T_DOUBLE", typestring="d")
1104 c_longdouble_type = CFloatType(8, typestring="g")
1106 c_null_ptr_type = CNullPtrType(c_void_type)
1107 c_char_array_type = CCharArrayType(None)
1108 c_char_ptr_type = CCharPtrType()
1109 c_utf8_char_array_type = CUTF8CharArrayType(None)
1110 c_char_ptr_ptr_type = CPtrType(c_char_ptr_type)
1111 c_py_ssize_t_ptr_type = CPtrType(c_py_ssize_t_type)
1112 c_int_ptr_type = CPtrType(c_int_type)
1114 c_returncode_type = CIntType(2, 1, "T_INT", is_returncode = 1)
1116 c_anon_enum_type = CAnonEnumType(-1, 1)
1118 # the Py_buffer type is defined in Builtin.py
1119 c_py_buffer_type = CStructOrUnionType("Py_buffer", "struct", None, 1, "Py_buffer")
1120 c_py_buffer_ptr_type = CPtrType(c_py_buffer_type)
1122 error_type = ErrorType()
1124 lowest_float_rank = 6
1126 sign_and_rank_to_type = {
1127 #(signed, rank)
1128 (0, 0, ): c_uchar_type,
1129 (0, 1): c_ushort_type,
1130 (0, 2): c_uint_type,
1131 (0, 3): c_ulong_type,
1132 (0, 4): c_ulonglong_type,
1133 (0, 5): c_ulonglong_type, # I'm not sure about this. this should be for size_t Py_ssize_t
1134 (1, 0): c_char_type,
1135 (1, 1): c_short_type,
1136 (1, 2): c_int_type,
1137 (1, 3): c_long_type,
1138 (1, 4): c_longlong_type,
1139 (1, 5): c_py_ssize_t_type,
1140 (2, 0): c_schar_type,
1141 (2, 1): c_sshort_type,
1142 (2, 2): c_sint_type,
1143 (2, 3): c_slong_type,
1144 (2, 4): c_slonglong_type,
1145 (2, 5): c_py_ssize_t_type,
1146 (1, 6): c_float_type,
1147 (1, 7): c_double_type,
1148 (1, 8): c_longdouble_type,
1151 modifiers_and_name_to_type = {
1152 #(signed, longness, name)
1153 (0, 0, "char"): c_uchar_type,
1154 (0, -1, "int"): c_ushort_type,
1155 (0, 0, "int"): c_uint_type,
1156 (0, 1, "int"): c_ulong_type,
1157 (0, 2, "int"): c_ulonglong_type,
1158 (1, 0, "void"): c_void_type,
1159 (1, 0, "char"): c_char_type,
1160 (1, -1, "int"): c_short_type,
1161 (1, 0, "int"): c_int_type,
1162 (1, 1, "int"): c_long_type,
1163 (1, 2, "int"): c_longlong_type,
1164 (1, 0, "Py_ssize_t"): c_py_ssize_t_type,
1165 (1, 0, "float"): c_float_type,
1166 (1, 0, "double"): c_double_type,
1167 (1, 1, "double"): c_longdouble_type,
1168 (1, 0, "object"): py_object_type,
1169 (1, 0, "bint"): c_bint_type,
1170 (2, 0, "char"): c_schar_type,
1171 (2, -1, "int"): c_sshort_type,
1172 (2, 0, "int"): c_sint_type,
1173 (2, 1, "int"): c_slong_type,
1174 (2, 2, "int"): c_slonglong_type,
1175 (2, 0, "Py_ssize_t"): c_py_ssize_t_type,
1178 def widest_numeric_type(type1, type2):
1179 # Given two numeric types, return the narrowest type
1180 # encompassing both of them.
1181 if type1.is_enum and type2.is_enum:
1182 widest_type = c_int_type
1183 elif type2.rank > type1.rank:
1184 widest_type = type2
1185 else:
1186 widest_type = type1
1187 return widest_type
1189 def simple_c_type(signed, longness, name):
1190 # Find type descriptor for simple type given name and modifiers.
1191 # Returns None if arguments don't make sense.
1192 return modifiers_and_name_to_type.get((signed, longness, name))
1194 def c_array_type(base_type, size):
1195 # Construct a C array type.
1196 if base_type is c_char_type:
1197 return CCharArrayType(size)
1198 else:
1199 return CArrayType(base_type, size)
1201 def c_ptr_type(base_type):
1202 # Construct a C pointer type.
1203 if base_type is c_char_type:
1204 return c_char_ptr_type
1205 else:
1206 return CPtrType(base_type)
1208 def public_decl(base, dll_linkage):
1209 if dll_linkage:
1210 return "%s(%s)" % (dll_linkage, base)
1211 else:
1212 return base
1214 def same_type(type1, type2):
1215 return type1.same_as(type2)
1217 def assignable_from(type1, type2):
1218 return type1.assignable_from(type2)
1220 def typecast(to_type, from_type, expr_code):
1221 # Return expr_code cast to a C type which can be
1222 # assigned to to_type, assuming its existing C type
1223 # is from_type.
1224 if to_type is from_type or \
1225 (not to_type.is_pyobject and assignable_from(to_type, from_type)):
1226 return expr_code
1227 else:
1228 #print "typecast: to", to_type, "from", from_type ###
1229 return to_type.cast_code(expr_code)
1232 type_conversion_predeclarations = """
1233 /* Type Conversion Predeclarations */
1235 #if PY_MAJOR_VERSION < 3
1236 #define __Pyx_PyBytes_FromString PyString_FromString
1237 #define __Pyx_PyBytes_AsString PyString_AsString
1238 #else
1239 #define __Pyx_PyBytes_FromString PyBytes_FromString
1240 #define __Pyx_PyBytes_AsString PyBytes_AsString
1241 #endif
1243 #define __Pyx_PyBool_FromLong(b) ((b) ? (Py_INCREF(Py_True), Py_True) : (Py_INCREF(Py_False), Py_False))
1244 static INLINE int __Pyx_PyObject_IsTrue(PyObject* x);
1245 static INLINE PY_LONG_LONG __pyx_PyInt_AsLongLong(PyObject* x);
1246 static INLINE unsigned PY_LONG_LONG __pyx_PyInt_AsUnsignedLongLong(PyObject* x);
1247 static INLINE Py_ssize_t __pyx_PyIndex_AsSsize_t(PyObject* b);
1249 #define __pyx_PyInt_AsLong(x) (PyInt_CheckExact(x) ? PyInt_AS_LONG(x) : PyInt_AsLong(x))
1250 #define __pyx_PyFloat_AsDouble(x) (PyFloat_CheckExact(x) ? PyFloat_AS_DOUBLE(x) : PyFloat_AsDouble(x))
1251 """ + type_conversion_predeclarations
1253 type_conversion_functions = """
1254 /* Type Conversion Functions */
1256 static INLINE Py_ssize_t __pyx_PyIndex_AsSsize_t(PyObject* b) {
1257 Py_ssize_t ival;
1258 PyObject* x = PyNumber_Index(b);
1259 if (!x) return -1;
1260 ival = PyInt_AsSsize_t(x);
1261 Py_DECREF(x);
1262 return ival;
1265 static INLINE int __Pyx_PyObject_IsTrue(PyObject* x) {
1266 if (x == Py_True) return 1;
1267 else if (x == Py_False) return 0;
1268 else return PyObject_IsTrue(x);
1271 static INLINE PY_LONG_LONG __pyx_PyInt_AsLongLong(PyObject* x) {
1272 if (PyInt_CheckExact(x)) {
1273 return PyInt_AS_LONG(x);
1275 else if (PyLong_CheckExact(x)) {
1276 return PyLong_AsLongLong(x);
1278 else {
1279 PY_LONG_LONG val;
1280 PyObject* tmp = PyNumber_Int(x); if (!tmp) return (PY_LONG_LONG)-1;
1281 val = __pyx_PyInt_AsLongLong(tmp);
1282 Py_DECREF(tmp);
1283 return val;
1287 static INLINE unsigned PY_LONG_LONG __pyx_PyInt_AsUnsignedLongLong(PyObject* x) {
1288 if (PyInt_CheckExact(x)) {
1289 long val = PyInt_AS_LONG(x);
1290 if (unlikely(val < 0)) {
1291 PyErr_SetString(PyExc_TypeError, "Negative assignment to unsigned type.");
1292 return (unsigned PY_LONG_LONG)-1;
1294 return val;
1296 else if (PyLong_CheckExact(x)) {
1297 return PyLong_AsUnsignedLongLong(x);
1299 else {
1300 PY_LONG_LONG val;
1301 PyObject* tmp = PyNumber_Int(x); if (!tmp) return (PY_LONG_LONG)-1;
1302 val = __pyx_PyInt_AsUnsignedLongLong(tmp);
1303 Py_DECREF(tmp);
1304 return val;
1308 """ + type_conversion_functions