OLD | NEW |
(Empty) | |
| 1 /////////////// BufferStructDeclare.proto /////////////// |
| 2 |
| 3 /* structs for buffer access */ |
| 4 |
| 5 typedef struct { |
| 6 Py_ssize_t shape, strides, suboffsets; |
| 7 } __Pyx_Buf_DimInfo; |
| 8 |
| 9 typedef struct { |
| 10 size_t refcount; |
| 11 Py_buffer pybuffer; |
| 12 } __Pyx_Buffer; |
| 13 |
| 14 typedef struct { |
| 15 __Pyx_Buffer *rcbuffer; |
| 16 char *data; |
| 17 __Pyx_Buf_DimInfo diminfo[{{max_dims}}]; |
| 18 } __Pyx_LocalBuf_ND; |
| 19 |
| 20 /////////////// BufferIndexError.proto /////////////// |
| 21 static void __Pyx_RaiseBufferIndexError(int axis); /*proto*/ |
| 22 |
| 23 /////////////// BufferIndexError /////////////// |
| 24 static void __Pyx_RaiseBufferIndexError(int axis) { |
| 25 PyErr_Format(PyExc_IndexError, |
| 26 "Out of bounds on buffer access (axis %d)", axis); |
| 27 } |
| 28 |
| 29 /////////////// BufferIndexErrorNogil.proto /////////////// |
| 30 //@requires: BufferIndexError |
| 31 |
| 32 static void __Pyx_RaiseBufferIndexErrorNogil(int axis); /*proto*/ |
| 33 |
| 34 /////////////// BufferIndexErrorNogil /////////////// |
| 35 static void __Pyx_RaiseBufferIndexErrorNogil(int axis) { |
| 36 #ifdef WITH_THREAD |
| 37 PyGILState_STATE gilstate = PyGILState_Ensure(); |
| 38 #endif |
| 39 __Pyx_RaiseBufferIndexError(axis); |
| 40 #ifdef WITH_THREAD |
| 41 PyGILState_Release(gilstate); |
| 42 #endif |
| 43 } |
| 44 |
| 45 /////////////// BufferFallbackError.proto /////////////// |
| 46 static void __Pyx_RaiseBufferFallbackError(void); /*proto*/ |
| 47 |
| 48 /////////////// BufferFallbackError /////////////// |
| 49 static void __Pyx_RaiseBufferFallbackError(void) { |
| 50 PyErr_SetString(PyExc_ValueError, |
| 51 "Buffer acquisition failed on assignment; and then reacquiring the old buff
er failed too!"); |
| 52 } |
| 53 |
| 54 /////////////// BufferFormatStructs.proto /////////////// |
| 55 |
| 56 #define IS_UNSIGNED(type) (((type) -1) > 0) |
| 57 |
| 58 /* Run-time type information about structs used with buffers */ |
| 59 struct __Pyx_StructField_; |
| 60 |
| 61 #define __PYX_BUF_FLAGS_PACKED_STRUCT (1 << 0) |
| 62 |
| 63 typedef struct { |
| 64 const char* name; /* for error messages only */ |
| 65 struct __Pyx_StructField_* fields; |
| 66 size_t size; /* sizeof(type) */ |
| 67 size_t arraysize[8]; /* length of array in each dimension */ |
| 68 int ndim; |
| 69 char typegroup; /* _R_eal, _C_omplex, Signed _I_nt, _U_nsigned int, _S_truct,
_P_ointer, _O_bject, c_H_ar */ |
| 70 char is_unsigned; |
| 71 int flags; |
| 72 } __Pyx_TypeInfo; |
| 73 |
| 74 typedef struct __Pyx_StructField_ { |
| 75 __Pyx_TypeInfo* type; |
| 76 const char* name; |
| 77 size_t offset; |
| 78 } __Pyx_StructField; |
| 79 |
| 80 typedef struct { |
| 81 __Pyx_StructField* field; |
| 82 size_t parent_offset; |
| 83 } __Pyx_BufFmt_StackElem; |
| 84 |
| 85 typedef struct { |
| 86 __Pyx_StructField root; |
| 87 __Pyx_BufFmt_StackElem* head; |
| 88 size_t fmt_offset; |
| 89 size_t new_count, enc_count; |
| 90 size_t struct_alignment; |
| 91 int is_complex; |
| 92 char enc_type; |
| 93 char new_packmode; |
| 94 char enc_packmode; |
| 95 char is_valid_array; |
| 96 } __Pyx_BufFmt_Context; |
| 97 |
| 98 /////////////// GetAndReleaseBuffer.proto /////////////// |
| 99 #if PY_MAJOR_VERSION < 3 |
| 100 static int __Pyx_GetBuffer(PyObject *obj, Py_buffer *view, int flags); |
| 101 static void __Pyx_ReleaseBuffer(Py_buffer *view); |
| 102 #else |
| 103 #define __Pyx_GetBuffer PyObject_GetBuffer |
| 104 #define __Pyx_ReleaseBuffer PyBuffer_Release |
| 105 #endif |
| 106 |
| 107 /////////////// GetAndReleaseBuffer /////////////// |
| 108 #if PY_MAJOR_VERSION < 3 |
| 109 static int __Pyx_GetBuffer(PyObject *obj, Py_buffer *view, int flags) { |
| 110 #if PY_VERSION_HEX >= 0x02060000 |
| 111 if (PyObject_CheckBuffer(obj)) return PyObject_GetBuffer(obj, view, flags); |
| 112 #endif |
| 113 |
| 114 {{for type_ptr, getbuffer, releasebuffer in types}} |
| 115 {{if getbuffer}} |
| 116 if (PyObject_TypeCheck(obj, {{type_ptr}})) return {{getbuffer}}(obj, vie
w, flags); |
| 117 {{endif}} |
| 118 {{endfor}} |
| 119 |
| 120 #if PY_VERSION_HEX < 0x02060000 |
| 121 if (obj->ob_type->tp_dict) { |
| 122 PyObject *getbuffer_cobj = PyObject_GetItem( |
| 123 obj->ob_type->tp_dict, PYIDENT("__pyx_getbuffer")); |
| 124 if (getbuffer_cobj) { |
| 125 getbufferproc func = (getbufferproc) PyCObject_AsVoidPtr(getbuffer_c
obj); |
| 126 Py_DECREF(getbuffer_cobj); |
| 127 if (!func) |
| 128 goto fail; |
| 129 |
| 130 return func(obj, view, flags); |
| 131 } else { |
| 132 PyErr_Clear(); |
| 133 } |
| 134 } |
| 135 #endif |
| 136 |
| 137 PyErr_Format(PyExc_TypeError, "'%.200s' does not have the buffer interface",
Py_TYPE(obj)->tp_name); |
| 138 |
| 139 #if PY_VERSION_HEX < 0x02060000 |
| 140 fail: |
| 141 #endif |
| 142 |
| 143 return -1; |
| 144 } |
| 145 |
| 146 static void __Pyx_ReleaseBuffer(Py_buffer *view) { |
| 147 PyObject *obj = view->obj; |
| 148 if (!obj) return; |
| 149 |
| 150 #if PY_VERSION_HEX >= 0x02060000 |
| 151 if (PyObject_CheckBuffer(obj)) { |
| 152 PyBuffer_Release(view); |
| 153 return; |
| 154 } |
| 155 #endif |
| 156 |
| 157 {{for type_ptr, getbuffer, releasebuffer in types}} |
| 158 {{if releasebuffer}} |
| 159 if (PyObject_TypeCheck(obj, {{type_ptr}})) { {{releasebuffer}}(obj, view
); return; } |
| 160 {{endif}} |
| 161 {{endfor}} |
| 162 |
| 163 #if PY_VERSION_HEX < 0x02060000 |
| 164 if (obj->ob_type->tp_dict) { |
| 165 PyObject *releasebuffer_cobj = PyObject_GetItem( |
| 166 obj->ob_type->tp_dict, PYIDENT("__pyx_releasebuffer")); |
| 167 if (releasebuffer_cobj) { |
| 168 releasebufferproc func = (releasebufferproc) PyCObject_AsVoidPtr(rel
easebuffer_cobj); |
| 169 Py_DECREF(releasebuffer_cobj); |
| 170 if (!func) |
| 171 goto fail; |
| 172 func(obj, view); |
| 173 return; |
| 174 } else { |
| 175 PyErr_Clear(); |
| 176 } |
| 177 } |
| 178 #endif |
| 179 |
| 180 goto nofail; |
| 181 |
| 182 #if PY_VERSION_HEX < 0x02060000 |
| 183 fail: |
| 184 #endif |
| 185 PyErr_WriteUnraisable(obj); |
| 186 |
| 187 nofail: |
| 188 Py_DECREF(obj); |
| 189 view->obj = NULL; |
| 190 } |
| 191 |
| 192 #endif /* PY_MAJOR_VERSION < 3 */ |
| 193 |
| 194 /////////////// BufferFormatCheck.proto /////////////// |
| 195 {{# |
| 196 |
| 197 Buffer format string checking |
| 198 |
| 199 Buffer type checking. Utility code for checking that acquired |
| 200 buffers match our assumptions. We only need to check ndim and |
| 201 the format string; the access mode/flags is checked by the |
| 202 exporter. See: |
| 203 |
| 204 http://docs.python.org/3/library/struct.html |
| 205 http://legacy.python.org/dev/peps/pep-3118/#additions-to-the-struct-string-s
yntax |
| 206 |
| 207 The alignment code is copied from _struct.c in Python. |
| 208 }} |
| 209 |
| 210 static CYTHON_INLINE int __Pyx_GetBufferAndValidate(Py_buffer* buf, PyObject* o
bj, |
| 211 __Pyx_TypeInfo* dtype, int flags, int nd, int cast, __Pyx_BufFmt_StackElem*
stack); |
| 212 static CYTHON_INLINE void __Pyx_SafeReleaseBuffer(Py_buffer* info); |
| 213 |
| 214 /////////////// BufferFormatCheck /////////////// |
| 215 static CYTHON_INLINE int __Pyx_IsLittleEndian(void) { |
| 216 unsigned int n = 1; |
| 217 return *(unsigned char*)(&n) != 0; |
| 218 } |
| 219 |
| 220 |
| 221 static void __Pyx_BufFmt_Init(__Pyx_BufFmt_Context* ctx, |
| 222 __Pyx_BufFmt_StackElem* stack, |
| 223 __Pyx_TypeInfo* type) { |
| 224 stack[0].field = &ctx->root; |
| 225 stack[0].parent_offset = 0; |
| 226 ctx->root.type = type; |
| 227 ctx->root.name = "buffer dtype"; |
| 228 ctx->root.offset = 0; |
| 229 ctx->head = stack; |
| 230 ctx->head->field = &ctx->root; |
| 231 ctx->fmt_offset = 0; |
| 232 ctx->head->parent_offset = 0; |
| 233 ctx->new_packmode = '@'; |
| 234 ctx->enc_packmode = '@'; |
| 235 ctx->new_count = 1; |
| 236 ctx->enc_count = 0; |
| 237 ctx->enc_type = 0; |
| 238 ctx->is_complex = 0; |
| 239 ctx->is_valid_array = 0; |
| 240 ctx->struct_alignment = 0; |
| 241 while (type->typegroup == 'S') { |
| 242 ++ctx->head; |
| 243 ctx->head->field = type->fields; |
| 244 ctx->head->parent_offset = 0; |
| 245 type = type->fields->type; |
| 246 } |
| 247 } |
| 248 |
| 249 static int __Pyx_BufFmt_ParseNumber(const char** ts) { |
| 250 int count; |
| 251 const char* t = *ts; |
| 252 if (*t < '0' || *t > '9') { |
| 253 return -1; |
| 254 } else { |
| 255 count = *t++ - '0'; |
| 256 while (*t >= '0' && *t < '9') { |
| 257 count *= 10; |
| 258 count += *t++ - '0'; |
| 259 } |
| 260 } |
| 261 *ts = t; |
| 262 return count; |
| 263 } |
| 264 |
| 265 static int __Pyx_BufFmt_ExpectNumber(const char **ts) { |
| 266 int number = __Pyx_BufFmt_ParseNumber(ts); |
| 267 if (number == -1) /* First char was not a digit */ |
| 268 PyErr_Format(PyExc_ValueError,\ |
| 269 "Does not understand character buffer dtype format string (
'%c')", **ts); |
| 270 return number; |
| 271 } |
| 272 |
| 273 |
| 274 static void __Pyx_BufFmt_RaiseUnexpectedChar(char ch) { |
| 275 PyErr_Format(PyExc_ValueError, |
| 276 "Unexpected format string character: '%c'", ch); |
| 277 } |
| 278 |
| 279 static const char* __Pyx_BufFmt_DescribeTypeChar(char ch, int is_complex) { |
| 280 switch (ch) { |
| 281 case 'c': return "'char'"; |
| 282 case 'b': return "'signed char'"; |
| 283 case 'B': return "'unsigned char'"; |
| 284 case 'h': return "'short'"; |
| 285 case 'H': return "'unsigned short'"; |
| 286 case 'i': return "'int'"; |
| 287 case 'I': return "'unsigned int'"; |
| 288 case 'l': return "'long'"; |
| 289 case 'L': return "'unsigned long'"; |
| 290 case 'q': return "'long long'"; |
| 291 case 'Q': return "'unsigned long long'"; |
| 292 case 'f': return (is_complex ? "'complex float'" : "'float'"); |
| 293 case 'd': return (is_complex ? "'complex double'" : "'double'"); |
| 294 case 'g': return (is_complex ? "'complex long double'" : "'long double'"); |
| 295 case 'T': return "a struct"; |
| 296 case 'O': return "Python object"; |
| 297 case 'P': return "a pointer"; |
| 298 case 's': case 'p': return "a string"; |
| 299 case 0: return "end"; |
| 300 default: return "unparseable format string"; |
| 301 } |
| 302 } |
| 303 |
| 304 static size_t __Pyx_BufFmt_TypeCharToStandardSize(char ch, int is_complex) { |
| 305 switch (ch) { |
| 306 case '?': case 'c': case 'b': case 'B': case 's': case 'p': return 1; |
| 307 case 'h': case 'H': return 2; |
| 308 case 'i': case 'I': case 'l': case 'L': return 4; |
| 309 case 'q': case 'Q': return 8; |
| 310 case 'f': return (is_complex ? 8 : 4); |
| 311 case 'd': return (is_complex ? 16 : 8); |
| 312 case 'g': { |
| 313 PyErr_SetString(PyExc_ValueError, "Python does not define a standard forma
t string size for long double ('g').."); |
| 314 return 0; |
| 315 } |
| 316 case 'O': case 'P': return sizeof(void*); |
| 317 default: |
| 318 __Pyx_BufFmt_RaiseUnexpectedChar(ch); |
| 319 return 0; |
| 320 } |
| 321 } |
| 322 |
| 323 static size_t __Pyx_BufFmt_TypeCharToNativeSize(char ch, int is_complex) { |
| 324 switch (ch) { |
| 325 case 'c': case 'b': case 'B': case 's': case 'p': return 1; |
| 326 case 'h': case 'H': return sizeof(short); |
| 327 case 'i': case 'I': return sizeof(int); |
| 328 case 'l': case 'L': return sizeof(long); |
| 329 #ifdef HAVE_LONG_LONG |
| 330 case 'q': case 'Q': return sizeof(PY_LONG_LONG); |
| 331 #endif |
| 332 case 'f': return sizeof(float) * (is_complex ? 2 : 1); |
| 333 case 'd': return sizeof(double) * (is_complex ? 2 : 1); |
| 334 case 'g': return sizeof(long double) * (is_complex ? 2 : 1); |
| 335 case 'O': case 'P': return sizeof(void*); |
| 336 default: { |
| 337 __Pyx_BufFmt_RaiseUnexpectedChar(ch); |
| 338 return 0; |
| 339 } |
| 340 } |
| 341 } |
| 342 |
| 343 typedef struct { char c; short x; } __Pyx_st_short; |
| 344 typedef struct { char c; int x; } __Pyx_st_int; |
| 345 typedef struct { char c; long x; } __Pyx_st_long; |
| 346 typedef struct { char c; float x; } __Pyx_st_float; |
| 347 typedef struct { char c; double x; } __Pyx_st_double; |
| 348 typedef struct { char c; long double x; } __Pyx_st_longdouble; |
| 349 typedef struct { char c; void *x; } __Pyx_st_void_p; |
| 350 #ifdef HAVE_LONG_LONG |
| 351 typedef struct { char c; PY_LONG_LONG x; } __Pyx_st_longlong; |
| 352 #endif |
| 353 |
| 354 static size_t __Pyx_BufFmt_TypeCharToAlignment(char ch, CYTHON_UNUSED int is_com
plex) { |
| 355 switch (ch) { |
| 356 case '?': case 'c': case 'b': case 'B': case 's': case 'p': return 1; |
| 357 case 'h': case 'H': return sizeof(__Pyx_st_short) - sizeof(short); |
| 358 case 'i': case 'I': return sizeof(__Pyx_st_int) - sizeof(int); |
| 359 case 'l': case 'L': return sizeof(__Pyx_st_long) - sizeof(long); |
| 360 #ifdef HAVE_LONG_LONG |
| 361 case 'q': case 'Q': return sizeof(__Pyx_st_longlong) - sizeof(PY_LONG_LONG); |
| 362 #endif |
| 363 case 'f': return sizeof(__Pyx_st_float) - sizeof(float); |
| 364 case 'd': return sizeof(__Pyx_st_double) - sizeof(double); |
| 365 case 'g': return sizeof(__Pyx_st_longdouble) - sizeof(long double); |
| 366 case 'P': case 'O': return sizeof(__Pyx_st_void_p) - sizeof(void*); |
| 367 default: |
| 368 __Pyx_BufFmt_RaiseUnexpectedChar(ch); |
| 369 return 0; |
| 370 } |
| 371 } |
| 372 |
| 373 /* These are for computing the padding at the end of the struct to align |
| 374 on the first member of the struct. This will probably the same as above, |
| 375 but we don't have any guarantees. |
| 376 */ |
| 377 typedef struct { short x; char c; } __Pyx_pad_short; |
| 378 typedef struct { int x; char c; } __Pyx_pad_int; |
| 379 typedef struct { long x; char c; } __Pyx_pad_long; |
| 380 typedef struct { float x; char c; } __Pyx_pad_float; |
| 381 typedef struct { double x; char c; } __Pyx_pad_double; |
| 382 typedef struct { long double x; char c; } __Pyx_pad_longdouble; |
| 383 typedef struct { void *x; char c; } __Pyx_pad_void_p; |
| 384 #ifdef HAVE_LONG_LONG |
| 385 typedef struct { PY_LONG_LONG x; char c; } __Pyx_pad_longlong; |
| 386 #endif |
| 387 |
| 388 static size_t __Pyx_BufFmt_TypeCharToPadding(char ch, CYTHON_UNUSED int is_compl
ex) { |
| 389 switch (ch) { |
| 390 case '?': case 'c': case 'b': case 'B': case 's': case 'p': return 1; |
| 391 case 'h': case 'H': return sizeof(__Pyx_pad_short) - sizeof(short); |
| 392 case 'i': case 'I': return sizeof(__Pyx_pad_int) - sizeof(int); |
| 393 case 'l': case 'L': return sizeof(__Pyx_pad_long) - sizeof(long); |
| 394 #ifdef HAVE_LONG_LONG |
| 395 case 'q': case 'Q': return sizeof(__Pyx_pad_longlong) - sizeof(PY_LONG_LONG)
; |
| 396 #endif |
| 397 case 'f': return sizeof(__Pyx_pad_float) - sizeof(float); |
| 398 case 'd': return sizeof(__Pyx_pad_double) - sizeof(double); |
| 399 case 'g': return sizeof(__Pyx_pad_longdouble) - sizeof(long double); |
| 400 case 'P': case 'O': return sizeof(__Pyx_pad_void_p) - sizeof(void*); |
| 401 default: |
| 402 __Pyx_BufFmt_RaiseUnexpectedChar(ch); |
| 403 return 0; |
| 404 } |
| 405 } |
| 406 |
| 407 static char __Pyx_BufFmt_TypeCharToGroup(char ch, int is_complex) { |
| 408 switch (ch) { |
| 409 case 'c': |
| 410 return 'H'; |
| 411 case 'b': case 'h': case 'i': |
| 412 case 'l': case 'q': case 's': case 'p': |
| 413 return 'I'; |
| 414 case 'B': case 'H': case 'I': case 'L': case 'Q': |
| 415 return 'U'; |
| 416 case 'f': case 'd': case 'g': |
| 417 return (is_complex ? 'C' : 'R'); |
| 418 case 'O': |
| 419 return 'O'; |
| 420 case 'P': |
| 421 return 'P'; |
| 422 default: { |
| 423 __Pyx_BufFmt_RaiseUnexpectedChar(ch); |
| 424 return 0; |
| 425 } |
| 426 } |
| 427 } |
| 428 |
| 429 |
| 430 static void __Pyx_BufFmt_RaiseExpected(__Pyx_BufFmt_Context* ctx) { |
| 431 if (ctx->head == NULL || ctx->head->field == &ctx->root) { |
| 432 const char* expected; |
| 433 const char* quote; |
| 434 if (ctx->head == NULL) { |
| 435 expected = "end"; |
| 436 quote = ""; |
| 437 } else { |
| 438 expected = ctx->head->field->type->name; |
| 439 quote = "'"; |
| 440 } |
| 441 PyErr_Format(PyExc_ValueError, |
| 442 "Buffer dtype mismatch, expected %s%s%s but got %s", |
| 443 quote, expected, quote, |
| 444 __Pyx_BufFmt_DescribeTypeChar(ctx->enc_type, ctx->is_complex)); |
| 445 } else { |
| 446 __Pyx_StructField* field = ctx->head->field; |
| 447 __Pyx_StructField* parent = (ctx->head - 1)->field; |
| 448 PyErr_Format(PyExc_ValueError, |
| 449 "Buffer dtype mismatch, expected '%s' but got %s in '%s.%s'", |
| 450 field->type->name, __Pyx_BufFmt_DescribeTypeChar(ctx->enc_type,
ctx->is_complex), |
| 451 parent->type->name, field->name); |
| 452 } |
| 453 } |
| 454 |
| 455 static int __Pyx_BufFmt_ProcessTypeChunk(__Pyx_BufFmt_Context* ctx) { |
| 456 char group; |
| 457 size_t size, offset, arraysize = 1; |
| 458 |
| 459 /* printf("processing... %s\n", ctx->head->field->type->name); */ |
| 460 |
| 461 if (ctx->enc_type == 0) return 0; |
| 462 |
| 463 /* Validate array size */ |
| 464 if (ctx->head->field->type->arraysize[0]) { |
| 465 int i, ndim = 0; |
| 466 |
| 467 /* handle strings ('s' and 'p') */ |
| 468 if (ctx->enc_type == 's' || ctx->enc_type == 'p') { |
| 469 ctx->is_valid_array = ctx->head->field->type->ndim == 1; |
| 470 ndim = 1; |
| 471 if (ctx->enc_count != ctx->head->field->type->arraysize[0]) { |
| 472 PyErr_Format(PyExc_ValueError, |
| 473 "Expected a dimension of size %zu, got %zu", |
| 474 ctx->head->field->type->arraysize[0], ctx->enc_count); |
| 475 return -1; |
| 476 } |
| 477 } |
| 478 |
| 479 if (!ctx->is_valid_array) { |
| 480 PyErr_Format(PyExc_ValueError, "Expected %d dimensions, got %d", |
| 481 ctx->head->field->type->ndim, ndim); |
| 482 return -1; |
| 483 } |
| 484 for (i = 0; i < ctx->head->field->type->ndim; i++) { |
| 485 arraysize *= ctx->head->field->type->arraysize[i]; |
| 486 } |
| 487 ctx->is_valid_array = 0; |
| 488 ctx->enc_count = 1; |
| 489 } |
| 490 |
| 491 group = __Pyx_BufFmt_TypeCharToGroup(ctx->enc_type, ctx->is_complex); |
| 492 do { |
| 493 __Pyx_StructField* field = ctx->head->field; |
| 494 __Pyx_TypeInfo* type = field->type; |
| 495 |
| 496 if (ctx->enc_packmode == '@' || ctx->enc_packmode == '^') { |
| 497 size = __Pyx_BufFmt_TypeCharToNativeSize(ctx->enc_type, ctx->is_complex); |
| 498 } else { |
| 499 size = __Pyx_BufFmt_TypeCharToStandardSize(ctx->enc_type, ctx->is_complex)
; |
| 500 } |
| 501 |
| 502 if (ctx->enc_packmode == '@') { |
| 503 size_t align_at = __Pyx_BufFmt_TypeCharToAlignment(ctx->enc_type, ctx->is_
complex); |
| 504 size_t align_mod_offset; |
| 505 if (align_at == 0) return -1; |
| 506 align_mod_offset = ctx->fmt_offset % align_at; |
| 507 if (align_mod_offset > 0) ctx->fmt_offset += align_at - align_mod_offset; |
| 508 |
| 509 if (ctx->struct_alignment == 0) |
| 510 ctx->struct_alignment = __Pyx_BufFmt_TypeCharToPadding(ctx->enc_type, |
| 511 ctx->is_complex
); |
| 512 } |
| 513 |
| 514 if (type->size != size || type->typegroup != group) { |
| 515 if (type->typegroup == 'C' && type->fields != NULL) { |
| 516 /* special case -- treat as struct rather than complex number */ |
| 517 size_t parent_offset = ctx->head->parent_offset + field->offset; |
| 518 ++ctx->head; |
| 519 ctx->head->field = type->fields; |
| 520 ctx->head->parent_offset = parent_offset; |
| 521 continue; |
| 522 } |
| 523 |
| 524 if ((type->typegroup == 'H' || group == 'H') && type->size == size) { |
| 525 /* special case -- chars don't care about sign */ |
| 526 } else { |
| 527 __Pyx_BufFmt_RaiseExpected(ctx); |
| 528 return -1; |
| 529 } |
| 530 } |
| 531 |
| 532 offset = ctx->head->parent_offset + field->offset; |
| 533 if (ctx->fmt_offset != offset) { |
| 534 PyErr_Format(PyExc_ValueError, |
| 535 "Buffer dtype mismatch; next field is at offset %" CYTHON_FOR
MAT_SSIZE_T "d but %" CYTHON_FORMAT_SSIZE_T "d expected", |
| 536 (Py_ssize_t)ctx->fmt_offset, (Py_ssize_t)offset); |
| 537 return -1; |
| 538 } |
| 539 |
| 540 ctx->fmt_offset += size; |
| 541 if (arraysize) |
| 542 ctx->fmt_offset += (arraysize - 1) * size; |
| 543 |
| 544 --ctx->enc_count; /* Consume from buffer string */ |
| 545 |
| 546 /* Done checking, move to next field, pushing or popping struct stack if nee
ded */ |
| 547 while (1) { |
| 548 if (field == &ctx->root) { |
| 549 ctx->head = NULL; |
| 550 if (ctx->enc_count != 0) { |
| 551 __Pyx_BufFmt_RaiseExpected(ctx); |
| 552 return -1; |
| 553 } |
| 554 break; /* breaks both loops as ctx->enc_count == 0 */ |
| 555 } |
| 556 ctx->head->field = ++field; |
| 557 if (field->type == NULL) { |
| 558 --ctx->head; |
| 559 field = ctx->head->field; |
| 560 continue; |
| 561 } else if (field->type->typegroup == 'S') { |
| 562 size_t parent_offset = ctx->head->parent_offset + field->offset; |
| 563 if (field->type->fields->type == NULL) continue; /* empty struct */ |
| 564 field = field->type->fields; |
| 565 ++ctx->head; |
| 566 ctx->head->field = field; |
| 567 ctx->head->parent_offset = parent_offset; |
| 568 break; |
| 569 } else { |
| 570 break; |
| 571 } |
| 572 } |
| 573 } while (ctx->enc_count); |
| 574 ctx->enc_type = 0; |
| 575 ctx->is_complex = 0; |
| 576 return 0; |
| 577 } |
| 578 |
| 579 /* Parse an array in the format string (e.g. (1,2,3)) */ |
| 580 static CYTHON_INLINE PyObject * |
| 581 __pyx_buffmt_parse_array(__Pyx_BufFmt_Context* ctx, const char** tsp) |
| 582 { |
| 583 const char *ts = *tsp; |
| 584 int i = 0, number; |
| 585 int ndim = ctx->head->field->type->ndim; |
| 586 ; |
| 587 ++ts; |
| 588 if (ctx->new_count != 1) { |
| 589 PyErr_SetString(PyExc_ValueError, |
| 590 "Cannot handle repeated arrays in format string"); |
| 591 return NULL; |
| 592 } |
| 593 |
| 594 /* Process the previous element */ |
| 595 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 596 |
| 597 /* Parse all numbers in the format string */ |
| 598 while (*ts && *ts != ')') { |
| 599 // ignore space characters (not using isspace() due to C/C++ problem on
MacOS-X) |
| 600 switch (*ts) { |
| 601 case ' ': case '\f': case '\r': case '\n': case '\t': case '\v': co
ntinue; |
| 602 default: break; /* not a 'break' in the loop */ |
| 603 } |
| 604 |
| 605 number = __Pyx_BufFmt_ExpectNumber(&ts); |
| 606 if (number == -1) return NULL; |
| 607 |
| 608 if (i < ndim && (size_t) number != ctx->head->field->type->arraysize[i]) |
| 609 return PyErr_Format(PyExc_ValueError, |
| 610 "Expected a dimension of size %zu, got %d", |
| 611 ctx->head->field->type->arraysize[i], number); |
| 612 |
| 613 if (*ts != ',' && *ts != ')') |
| 614 return PyErr_Format(PyExc_ValueError, |
| 615 "Expected a comma in format string, got '%c'", *
ts); |
| 616 |
| 617 if (*ts == ',') ts++; |
| 618 i++; |
| 619 } |
| 620 |
| 621 if (i != ndim) |
| 622 return PyErr_Format(PyExc_ValueError, "Expected %d dimension(s), got %d"
, |
| 623 ctx->head->field->type->ndim, i); |
| 624 |
| 625 if (!*ts) { |
| 626 PyErr_SetString(PyExc_ValueError, |
| 627 "Unexpected end of format string, expected ')'"); |
| 628 return NULL; |
| 629 } |
| 630 |
| 631 ctx->is_valid_array = 1; |
| 632 ctx->new_count = 1; |
| 633 *tsp = ++ts; |
| 634 return Py_None; |
| 635 } |
| 636 |
| 637 static const char* __Pyx_BufFmt_CheckString(__Pyx_BufFmt_Context* ctx, const cha
r* ts) { |
| 638 int got_Z = 0; |
| 639 |
| 640 while (1) { |
| 641 /* puts(ts); */ |
| 642 switch(*ts) { |
| 643 case 0: |
| 644 if (ctx->enc_type != 0 && ctx->head == NULL) { |
| 645 __Pyx_BufFmt_RaiseExpected(ctx); |
| 646 return NULL; |
| 647 } |
| 648 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 649 if (ctx->head != NULL) { |
| 650 __Pyx_BufFmt_RaiseExpected(ctx); |
| 651 return NULL; |
| 652 } |
| 653 return ts; |
| 654 case ' ': |
| 655 case '\r': |
| 656 case '\n': |
| 657 ++ts; |
| 658 break; |
| 659 case '<': |
| 660 if (!__Pyx_IsLittleEndian()) { |
| 661 PyErr_SetString(PyExc_ValueError, "Little-endian buffer not supported
on big-endian compiler"); |
| 662 return NULL; |
| 663 } |
| 664 ctx->new_packmode = '='; |
| 665 ++ts; |
| 666 break; |
| 667 case '>': |
| 668 case '!': |
| 669 if (__Pyx_IsLittleEndian()) { |
| 670 PyErr_SetString(PyExc_ValueError, "Big-endian buffer not supported on
little-endian compiler"); |
| 671 return NULL; |
| 672 } |
| 673 ctx->new_packmode = '='; |
| 674 ++ts; |
| 675 break; |
| 676 case '=': |
| 677 case '@': |
| 678 case '^': |
| 679 ctx->new_packmode = *ts++; |
| 680 break; |
| 681 case 'T': /* substruct */ |
| 682 { |
| 683 const char* ts_after_sub; |
| 684 size_t i, struct_count = ctx->new_count; |
| 685 size_t struct_alignment = ctx->struct_alignment; |
| 686 ctx->new_count = 1; |
| 687 ++ts; |
| 688 if (*ts != '{') { |
| 689 PyErr_SetString(PyExc_ValueError, "Buffer acquisition: Expected '{'
after 'T'"); |
| 690 return NULL; |
| 691 } |
| 692 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 693 ctx->enc_type = 0; /* Erase processed last struct element */ |
| 694 ctx->enc_count = 0; |
| 695 ctx->struct_alignment = 0; |
| 696 ++ts; |
| 697 ts_after_sub = ts; |
| 698 for (i = 0; i != struct_count; ++i) { |
| 699 ts_after_sub = __Pyx_BufFmt_CheckString(ctx, ts); |
| 700 if (!ts_after_sub) return NULL; |
| 701 } |
| 702 ts = ts_after_sub; |
| 703 if (struct_alignment) ctx->struct_alignment = struct_alignment; |
| 704 } |
| 705 break; |
| 706 case '}': /* end of substruct; either repeat or move on */ |
| 707 { |
| 708 size_t alignment = ctx->struct_alignment; |
| 709 ++ts; |
| 710 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 711 ctx->enc_type = 0; /* Erase processed last struct element */ |
| 712 if (alignment && ctx->fmt_offset % alignment) { |
| 713 /* Pad struct on size of the first member */ |
| 714 ctx->fmt_offset += alignment - (ctx->fmt_offset % alignment); |
| 715 } |
| 716 } |
| 717 return ts; |
| 718 case 'x': |
| 719 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 720 ctx->fmt_offset += ctx->new_count; |
| 721 ctx->new_count = 1; |
| 722 ctx->enc_count = 0; |
| 723 ctx->enc_type = 0; |
| 724 ctx->enc_packmode = ctx->new_packmode; |
| 725 ++ts; |
| 726 break; |
| 727 case 'Z': |
| 728 got_Z = 1; |
| 729 ++ts; |
| 730 if (*ts != 'f' && *ts != 'd' && *ts != 'g') { |
| 731 __Pyx_BufFmt_RaiseUnexpectedChar('Z'); |
| 732 return NULL; |
| 733 } |
| 734 /* fall through */ |
| 735 case 'c': case 'b': case 'B': case 'h': case 'H': case 'i': case 'I': |
| 736 case 'l': case 'L': case 'q': case 'Q': |
| 737 case 'f': case 'd': case 'g': |
| 738 case 'O': case 'p': |
| 739 if (ctx->enc_type == *ts && got_Z == ctx->is_complex && |
| 740 ctx->enc_packmode == ctx->new_packmode) { |
| 741 /* Continue pooling same type */ |
| 742 ctx->enc_count += ctx->new_count; |
| 743 ctx->new_count = 1; |
| 744 got_Z = 0; |
| 745 ++ts; |
| 746 break; |
| 747 } |
| 748 /* fall through */ |
| 749 case 's': |
| 750 /* 's' or new type (cannot be added to current pool) */ |
| 751 if (__Pyx_BufFmt_ProcessTypeChunk(ctx) == -1) return NULL; |
| 752 ctx->enc_count = ctx->new_count; |
| 753 ctx->enc_packmode = ctx->new_packmode; |
| 754 ctx->enc_type = *ts; |
| 755 ctx->is_complex = got_Z; |
| 756 ++ts; |
| 757 ctx->new_count = 1; |
| 758 got_Z = 0; |
| 759 break; |
| 760 case ':': |
| 761 ++ts; |
| 762 while(*ts != ':') ++ts; |
| 763 ++ts; |
| 764 break; |
| 765 case '(': |
| 766 if (!__pyx_buffmt_parse_array(ctx, &ts)) return NULL; |
| 767 break; |
| 768 default: |
| 769 { |
| 770 int number = __Pyx_BufFmt_ExpectNumber(&ts); |
| 771 if (number == -1) return NULL; |
| 772 ctx->new_count = (size_t)number; |
| 773 } |
| 774 } |
| 775 } |
| 776 } |
| 777 |
| 778 static CYTHON_INLINE void __Pyx_ZeroBuffer(Py_buffer* buf) { |
| 779 buf->buf = NULL; |
| 780 buf->obj = NULL; |
| 781 buf->strides = __Pyx_zeros; |
| 782 buf->shape = __Pyx_zeros; |
| 783 buf->suboffsets = __Pyx_minusones; |
| 784 } |
| 785 |
| 786 static CYTHON_INLINE int __Pyx_GetBufferAndValidate( |
| 787 Py_buffer* buf, PyObject* obj, __Pyx_TypeInfo* dtype, int flags, |
| 788 int nd, int cast, __Pyx_BufFmt_StackElem* stack) |
| 789 { |
| 790 if (obj == Py_None || obj == NULL) { |
| 791 __Pyx_ZeroBuffer(buf); |
| 792 return 0; |
| 793 } |
| 794 buf->buf = NULL; |
| 795 if (__Pyx_GetBuffer(obj, buf, flags) == -1) goto fail; |
| 796 if (buf->ndim != nd) { |
| 797 PyErr_Format(PyExc_ValueError, |
| 798 "Buffer has wrong number of dimensions (expected %d, got %d)", |
| 799 nd, buf->ndim); |
| 800 goto fail; |
| 801 } |
| 802 if (!cast) { |
| 803 __Pyx_BufFmt_Context ctx; |
| 804 __Pyx_BufFmt_Init(&ctx, stack, dtype); |
| 805 if (!__Pyx_BufFmt_CheckString(&ctx, buf->format)) goto fail; |
| 806 } |
| 807 if ((unsigned)buf->itemsize != dtype->size) { |
| 808 PyErr_Format(PyExc_ValueError, |
| 809 "Item size of buffer (%" CYTHON_FORMAT_SSIZE_T "d byte%s) does not match s
ize of '%s' (%" CYTHON_FORMAT_SSIZE_T "d byte%s)", |
| 810 buf->itemsize, (buf->itemsize > 1) ? "s" : "", |
| 811 dtype->name, (Py_ssize_t)dtype->size, (dtype->size > 1) ? "s" : ""); |
| 812 goto fail; |
| 813 } |
| 814 if (buf->suboffsets == NULL) buf->suboffsets = __Pyx_minusones; |
| 815 return 0; |
| 816 fail:; |
| 817 __Pyx_ZeroBuffer(buf); |
| 818 return -1; |
| 819 } |
| 820 |
| 821 static CYTHON_INLINE void __Pyx_SafeReleaseBuffer(Py_buffer* info) { |
| 822 if (info->buf == NULL) return; |
| 823 if (info->suboffsets == __Pyx_minusones) info->suboffsets = NULL; |
| 824 __Pyx_ReleaseBuffer(info); |
| 825 } |
| 826 |
| 827 /////////////// TypeInfoCompare.proto /////////////// |
| 828 static int __pyx_typeinfo_cmp(__Pyx_TypeInfo *a, __Pyx_TypeInfo *b); |
| 829 |
| 830 /////////////// TypeInfoCompare /////////////// |
| 831 /* See if two dtypes are equal */ |
| 832 static int |
| 833 __pyx_typeinfo_cmp(__Pyx_TypeInfo *a, __Pyx_TypeInfo *b) |
| 834 { |
| 835 int i; |
| 836 |
| 837 if (!a || !b) |
| 838 return 0; |
| 839 |
| 840 if (a == b) |
| 841 return 1; |
| 842 |
| 843 if (a->size != b->size || a->typegroup != b->typegroup || |
| 844 a->is_unsigned != b->is_unsigned || a->ndim != b->ndim) { |
| 845 if (a->typegroup == 'H' || b->typegroup == 'H') { |
| 846 /* Special case for chars */ |
| 847 return a->size == b->size; |
| 848 } else { |
| 849 return 0; |
| 850 } |
| 851 } |
| 852 |
| 853 if (a->ndim) { |
| 854 /* Verify multidimensional C arrays */ |
| 855 for (i = 0; i < a->ndim; i++) |
| 856 if (a->arraysize[i] != b->arraysize[i]) |
| 857 return 0; |
| 858 } |
| 859 |
| 860 if (a->typegroup == 'S') { |
| 861 /* Check for packed struct */ |
| 862 if (a->flags != b->flags) |
| 863 return 0; |
| 864 |
| 865 /* compare all struct fields */ |
| 866 if (a->fields || b->fields) { |
| 867 /* Check if both have fields */ |
| 868 if (!(a->fields && b->fields)) |
| 869 return 0; |
| 870 |
| 871 /* compare */ |
| 872 for (i = 0; a->fields[i].type && b->fields[i].type; i++) { |
| 873 __Pyx_StructField *field_a = a->fields + i; |
| 874 __Pyx_StructField *field_b = b->fields + i; |
| 875 |
| 876 if (field_a->offset != field_b->offset || |
| 877 !__pyx_typeinfo_cmp(field_a->type, field_b->type)) |
| 878 return 0; |
| 879 } |
| 880 |
| 881 /* If all fields are processed, we have a match */ |
| 882 return !a->fields[i].type && !b->fields[i].type; |
| 883 } |
| 884 } |
| 885 |
| 886 return 1; |
| 887 } |
| 888 |
| 889 |
| 890 |
| 891 /////////////// TypeInfoToFormat.proto /////////////// |
| 892 struct __pyx_typeinfo_string { |
| 893 char string[3]; |
| 894 }; |
| 895 static struct __pyx_typeinfo_string __Pyx_TypeInfoToFormat(__Pyx_TypeInfo *type)
; |
| 896 |
| 897 /////////////// TypeInfoToFormat /////////////// |
| 898 {{# See also MemoryView.pyx:BufferFormatFromTypeInfo }} |
| 899 |
| 900 static struct __pyx_typeinfo_string __Pyx_TypeInfoToFormat(__Pyx_TypeInfo *type)
{ |
| 901 struct __pyx_typeinfo_string result = { {0} }; |
| 902 char *buf = (char *) result.string; |
| 903 size_t size = type->size; |
| 904 |
| 905 switch (type->typegroup) { |
| 906 case 'H': |
| 907 *buf = 'c'; |
| 908 break; |
| 909 case 'I': |
| 910 case 'U': |
| 911 if (size == 1) |
| 912 *buf = 'b'; |
| 913 else if (size == 2) |
| 914 *buf = 'h'; |
| 915 else if (size == 4) |
| 916 *buf = 'i'; |
| 917 else if (size == 8) |
| 918 *buf = 'q'; |
| 919 |
| 920 if (type->is_unsigned) |
| 921 *buf = toupper(*buf); |
| 922 break; |
| 923 case 'P': |
| 924 *buf = 'P'; |
| 925 break; |
| 926 case 'C': |
| 927 { |
| 928 __Pyx_TypeInfo complex_type = *type; |
| 929 complex_type.typegroup = 'R'; |
| 930 complex_type.size /= 2; |
| 931 |
| 932 *buf++ = 'Z'; |
| 933 *buf = __Pyx_TypeInfoToFormat(&complex_type).string[0]; |
| 934 break; |
| 935 } |
| 936 case 'R': |
| 937 if (size == 4) |
| 938 *buf = 'f'; |
| 939 else if (size == 8) |
| 940 *buf = 'd'; |
| 941 else |
| 942 *buf = 'g'; |
| 943 break; |
| 944 } |
| 945 |
| 946 return result; |
| 947 } |
OLD | NEW |