Nuitka
The Python compiler
Loading...
Searching...
No Matches
HelpersOperationBinaryTruediv.c
1// Copyright 2025, Kay Hayen, mailto:kay.hayen@gmail.com find license text at end of file
2
3/* WARNING, this code is GENERATED. Modify the template HelperOperationBinary.c.j2 instead! */
4
5/* This file is included from another C file, help IDEs to still parse it on its own. */
6#ifdef __IDE_ONLY__
7#include "nuitka/prelude.h"
8#endif
9
10/* C helpers for type specialized "/" (TRUEDIV) operations */
11
12#if PYTHON_VERSION < 0x300
13/* Code referring to "INT" corresponds to Python2 'int' and "INT" to Python2 'int'. */
14static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_INT_INT(PyObject *operand1, PyObject *operand2) {
15 CHECK_OBJECT(operand1);
16 assert(PyInt_CheckExact(operand1));
17 CHECK_OBJECT(operand2);
18 assert(PyInt_CheckExact(operand2));
19
20 PyObject *result;
21
22 // Not every code path will make use of all possible results.
23#if defined(_MSC_VER)
24#pragma warning(push)
25#pragma warning(disable : 4101)
26#endif
27 NUITKA_MAY_BE_UNUSED bool cbool_result;
28 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
29 NUITKA_MAY_BE_UNUSED long clong_result;
30 NUITKA_MAY_BE_UNUSED double cfloat_result;
31#if defined(_MSC_VER)
32#pragma warning(pop)
33#endif
34
35 CHECK_OBJECT(operand1);
36 assert(PyInt_CheckExact(operand1));
37 CHECK_OBJECT(operand2);
38 assert(PyInt_CheckExact(operand2));
39
40 const long a = PyInt_AS_LONG(operand1);
41 const long b = PyInt_AS_LONG(operand2);
42
43 if (unlikely(b == 0)) {
44 PyThreadState *tstate = PyThreadState_GET();
45
46 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
47 goto exit_result_exception;
48 }
49
50 if (a == 0) {
51 if (b < 0) {
52 goto exit_result_ok_const_float_minus_0_0;
53 } else {
54 goto exit_result_ok_const_float_0_0;
55 }
56 }
57
58/* May need to resort to LONG code, which we currently do not
59 * specialize yet. TODO: Once we do that, call it here instead.
60 */
61#if DBL_MANT_DIG < WIDTH_OF_ULONG
62 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
63 } else
64#endif
65 {
66 double r = (double)a / (double)b;
67
68 cfloat_result = r;
69 goto exit_result_ok_cfloat;
70 }
71
72 {
73 PyObject *operand1_object = operand1;
74 PyObject *operand2_object = operand2;
75
76 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
77 assert(r != Py_NotImplemented);
78
79 obj_result = r;
80 goto exit_result_object;
81 }
82
83exit_result_ok_cfloat:
84 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
85 goto exit_result_ok;
86
87exit_result_object:
88 if (unlikely(obj_result == NULL)) {
89 goto exit_result_exception;
90 }
91 result = obj_result;
92 goto exit_result_ok;
93
94exit_result_ok_const_float_0_0:
95 Py_INCREF(const_float_0_0);
96 result = const_float_0_0;
97 goto exit_result_ok;
98
99exit_result_ok_const_float_minus_0_0:
100 Py_INCREF(const_float_minus_0_0);
101 result = const_float_minus_0_0;
102 goto exit_result_ok;
103
104exit_result_ok:
105 return result;
106
107exit_result_exception:
108 return NULL;
109}
110
111PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_INT_INT(PyObject *operand1, PyObject *operand2) {
112 return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_INT(operand1, operand2);
113}
114#endif
115
116#if PYTHON_VERSION < 0x300
117/* Code referring to "OBJECT" corresponds to any Python object and "INT" to Python2 'int'. */
118static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_INT(PyObject *operand1,
119 PyObject *operand2) {
120 PyTypeObject *type1 = Py_TYPE(operand1);
121
122#if defined(_MSC_VER)
123#pragma warning(push)
124#pragma warning(disable : 4101)
125#endif
126 NUITKA_MAY_BE_UNUSED bool cbool_result;
127 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
128#if defined(_MSC_VER)
129#pragma warning(pop)
130#endif
131
132 binaryfunc slot1 =
133 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_true_divide : NULL;
134 binaryfunc slot2 = NULL;
135
136 if (!(type1 == &PyInt_Type)) {
137 // Different types, need to consider second value slot.
138
139 slot2 = PyInt_Type.tp_as_number->nb_true_divide;
140
141 if (slot1 == slot2) {
142 slot2 = NULL;
143 }
144 }
145
146 if (slot1 != NULL) {
147 PyObject *x = slot1(operand1, operand2);
148
149 if (x != Py_NotImplemented) {
150 obj_result = x;
151 goto exit_binary_result_object;
152 }
153
154 Py_DECREF_IMMORTAL(x);
155 }
156
157 if (slot2 != NULL) {
158 PyObject *x = slot2(operand1, operand2);
159
160 if (x != Py_NotImplemented) {
161 obj_result = x;
162 goto exit_binary_result_object;
163 }
164
165 Py_DECREF_IMMORTAL(x);
166 }
167
168#if PYTHON_VERSION < 0x300
169 if (!NEW_STYLE_NUMBER_TYPE(type1) || !1) {
170 coercion c1 =
171 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_coerce : NULL;
172
173 if (c1 != NULL) {
174 PyObject *coerced1 = operand1;
175 PyObject *coerced2 = operand2;
176
177 int err = c1(&coerced1, &coerced2);
178
179 if (unlikely(err < 0)) {
180 goto exit_binary_exception;
181 }
182
183 if (err == 0) {
184 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
185
186 if (likely(mv == NULL)) {
187 binaryfunc slot = mv->nb_true_divide;
188
189 if (likely(slot != NULL)) {
190 PyObject *x = slot(coerced1, coerced2);
191
192 Py_DECREF(coerced1);
193 Py_DECREF(coerced2);
194
195 obj_result = x;
196 goto exit_binary_result_object;
197 }
198 }
199
200 // nb_coerce took a reference.
201 Py_DECREF(coerced1);
202 Py_DECREF(coerced2);
203 }
204 }
205 coercion c2 = PyInt_Type.tp_as_number->nb_coerce;
206
207 if (c2 != NULL) {
208 PyObject *coerced1 = operand1;
209 PyObject *coerced2 = operand2;
210
211 int err = c2(&coerced2, &coerced1);
212
213 if (unlikely(err < 0)) {
214 goto exit_binary_exception;
215 }
216
217 if (err == 0) {
218 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
219
220 if (likely(mv == NULL)) {
221 binaryfunc slot = mv->nb_true_divide;
222
223 if (likely(slot != NULL)) {
224 PyObject *x = slot(coerced1, coerced2);
225
226 Py_DECREF(coerced1);
227 Py_DECREF(coerced2);
228
229 obj_result = x;
230 goto exit_binary_result_object;
231 }
232 }
233
234 // nb_coerce took a reference.
235 Py_DECREF(coerced1);
236 Py_DECREF(coerced2);
237 }
238 }
239 }
240#endif
241
242 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: '%s' and 'int'", type1->tp_name);
243 goto exit_binary_exception;
244
245exit_binary_result_object:
246 return obj_result;
247
248exit_binary_exception:
249 return NULL;
250}
251static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_INT(PyObject *operand1, PyObject *operand2) {
252 CHECK_OBJECT(operand1);
253 CHECK_OBJECT(operand2);
254 assert(PyInt_CheckExact(operand2));
255
256 PyTypeObject *type1 = Py_TYPE(operand1);
257
258 if (type1 == &PyInt_Type) {
259 PyObject *result;
260
261 // return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_INT(operand1, operand2);
262
263 // Not every code path will make use of all possible results.
264#if defined(_MSC_VER)
265#pragma warning(push)
266#pragma warning(disable : 4101)
267#endif
268 NUITKA_MAY_BE_UNUSED bool cbool_result;
269 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
270 NUITKA_MAY_BE_UNUSED long clong_result;
271 NUITKA_MAY_BE_UNUSED double cfloat_result;
272#if defined(_MSC_VER)
273#pragma warning(pop)
274#endif
275
276 CHECK_OBJECT(operand1);
277 assert(PyInt_CheckExact(operand1));
278 CHECK_OBJECT(operand2);
279 assert(PyInt_CheckExact(operand2));
280
281 const long a = PyInt_AS_LONG(operand1);
282 const long b = PyInt_AS_LONG(operand2);
283
284 if (unlikely(b == 0)) {
285 PyThreadState *tstate = PyThreadState_GET();
286
287 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
288 goto exit_result_exception;
289 }
290
291 if (a == 0) {
292 if (b < 0) {
293 goto exit_result_ok_const_float_minus_0_0;
294 } else {
295 goto exit_result_ok_const_float_0_0;
296 }
297 }
298
299/* May need to resort to LONG code, which we currently do not
300 * specialize yet. TODO: Once we do that, call it here instead.
301 */
302#if DBL_MANT_DIG < WIDTH_OF_ULONG
303 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
304 } else
305#endif
306 {
307 double r = (double)a / (double)b;
308
309 cfloat_result = r;
310 goto exit_result_ok_cfloat;
311 }
312
313 {
314 PyObject *operand1_object = operand1;
315 PyObject *operand2_object = operand2;
316
317 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
318 assert(r != Py_NotImplemented);
319
320 obj_result = r;
321 goto exit_result_object;
322 }
323
324 exit_result_ok_cfloat:
325 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
326 goto exit_result_ok;
327
328 exit_result_object:
329 if (unlikely(obj_result == NULL)) {
330 goto exit_result_exception;
331 }
332 result = obj_result;
333 goto exit_result_ok;
334
335 exit_result_ok_const_float_0_0:
336 Py_INCREF(const_float_0_0);
337 result = const_float_0_0;
338 goto exit_result_ok;
339
340 exit_result_ok_const_float_minus_0_0:
341 Py_INCREF(const_float_minus_0_0);
342 result = const_float_minus_0_0;
343 goto exit_result_ok;
344
345 exit_result_ok:
346 return result;
347
348 exit_result_exception:
349 return NULL;
350 }
351
352 return __BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_INT(operand1, operand2);
353}
354
355PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_INT(PyObject *operand1, PyObject *operand2) {
356 return _BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_INT(operand1, operand2);
357}
358#endif
359
360#if PYTHON_VERSION < 0x300
361/* Code referring to "INT" corresponds to Python2 'int' and "OBJECT" to any Python object. */
362static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_INT_OBJECT(PyObject *operand1,
363 PyObject *operand2) {
364 PyTypeObject *type2 = Py_TYPE(operand2);
365
366#if defined(_MSC_VER)
367#pragma warning(push)
368#pragma warning(disable : 4101)
369#endif
370 NUITKA_MAY_BE_UNUSED bool cbool_result;
371 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
372#if defined(_MSC_VER)
373#pragma warning(pop)
374#endif
375
376 binaryfunc slot1 = PyInt_Type.tp_as_number->nb_true_divide;
377 binaryfunc slot2 = NULL;
378
379 if (!(&PyInt_Type == type2)) {
380 // Different types, need to consider second value slot.
381
382 slot2 =
383 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_true_divide : NULL;
384
385 if (slot1 == slot2) {
386 slot2 = NULL;
387 }
388 }
389
390 if (slot1 != NULL) {
391 if (slot2 != NULL) {
392 if (Nuitka_Type_IsSubtype(type2, &PyInt_Type)) {
393 PyObject *x = slot2(operand1, operand2);
394
395 if (x != Py_NotImplemented) {
396 obj_result = x;
397 goto exit_binary_result_object;
398 }
399
400 Py_DECREF_IMMORTAL(x);
401 slot2 = NULL;
402 }
403 }
404
405 PyObject *x = slot1(operand1, operand2);
406
407 if (x != Py_NotImplemented) {
408 obj_result = x;
409 goto exit_binary_result_object;
410 }
411
412 Py_DECREF_IMMORTAL(x);
413 }
414
415 if (slot2 != NULL) {
416 PyObject *x = slot2(operand1, operand2);
417
418 if (x != Py_NotImplemented) {
419 obj_result = x;
420 goto exit_binary_result_object;
421 }
422
423 Py_DECREF_IMMORTAL(x);
424 }
425
426#if PYTHON_VERSION < 0x300
427 if (!1 || !NEW_STYLE_NUMBER_TYPE(type2)) {
428 coercion c1 = PyInt_Type.tp_as_number->nb_coerce;
429
430 if (c1 != NULL) {
431 PyObject *coerced1 = operand1;
432 PyObject *coerced2 = operand2;
433
434 int err = c1(&coerced1, &coerced2);
435
436 if (unlikely(err < 0)) {
437 goto exit_binary_exception;
438 }
439
440 if (err == 0) {
441 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
442
443 if (likely(mv == NULL)) {
444 binaryfunc slot = mv->nb_true_divide;
445
446 if (likely(slot != NULL)) {
447 PyObject *x = slot(coerced1, coerced2);
448
449 Py_DECREF(coerced1);
450 Py_DECREF(coerced2);
451
452 obj_result = x;
453 goto exit_binary_result_object;
454 }
455 }
456
457 // nb_coerce took a reference.
458 Py_DECREF(coerced1);
459 Py_DECREF(coerced2);
460 }
461 }
462 coercion c2 =
463 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_coerce : NULL;
464
465 if (c2 != NULL) {
466 PyObject *coerced1 = operand1;
467 PyObject *coerced2 = operand2;
468
469 int err = c2(&coerced2, &coerced1);
470
471 if (unlikely(err < 0)) {
472 goto exit_binary_exception;
473 }
474
475 if (err == 0) {
476 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
477
478 if (likely(mv == NULL)) {
479 binaryfunc slot = mv->nb_true_divide;
480
481 if (likely(slot != NULL)) {
482 PyObject *x = slot(coerced1, coerced2);
483
484 Py_DECREF(coerced1);
485 Py_DECREF(coerced2);
486
487 obj_result = x;
488 goto exit_binary_result_object;
489 }
490 }
491
492 // nb_coerce took a reference.
493 Py_DECREF(coerced1);
494 Py_DECREF(coerced2);
495 }
496 }
497 }
498#endif
499
500 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'int' and '%s'", type2->tp_name);
501 goto exit_binary_exception;
502
503exit_binary_result_object:
504 return obj_result;
505
506exit_binary_exception:
507 return NULL;
508}
509static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_INT_OBJECT(PyObject *operand1, PyObject *operand2) {
510 CHECK_OBJECT(operand1);
511 assert(PyInt_CheckExact(operand1));
512 CHECK_OBJECT(operand2);
513
514 PyTypeObject *type2 = Py_TYPE(operand2);
515
516 if (&PyInt_Type == type2) {
517 PyObject *result;
518
519 // return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_INT(operand1, operand2);
520
521 // Not every code path will make use of all possible results.
522#if defined(_MSC_VER)
523#pragma warning(push)
524#pragma warning(disable : 4101)
525#endif
526 NUITKA_MAY_BE_UNUSED bool cbool_result;
527 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
528 NUITKA_MAY_BE_UNUSED long clong_result;
529 NUITKA_MAY_BE_UNUSED double cfloat_result;
530#if defined(_MSC_VER)
531#pragma warning(pop)
532#endif
533
534 CHECK_OBJECT(operand1);
535 assert(PyInt_CheckExact(operand1));
536 CHECK_OBJECT(operand2);
537 assert(PyInt_CheckExact(operand2));
538
539 const long a = PyInt_AS_LONG(operand1);
540 const long b = PyInt_AS_LONG(operand2);
541
542 if (unlikely(b == 0)) {
543 PyThreadState *tstate = PyThreadState_GET();
544
545 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
546 goto exit_result_exception;
547 }
548
549 if (a == 0) {
550 if (b < 0) {
551 goto exit_result_ok_const_float_minus_0_0;
552 } else {
553 goto exit_result_ok_const_float_0_0;
554 }
555 }
556
557/* May need to resort to LONG code, which we currently do not
558 * specialize yet. TODO: Once we do that, call it here instead.
559 */
560#if DBL_MANT_DIG < WIDTH_OF_ULONG
561 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
562 } else
563#endif
564 {
565 double r = (double)a / (double)b;
566
567 cfloat_result = r;
568 goto exit_result_ok_cfloat;
569 }
570
571 {
572 PyObject *operand1_object = operand1;
573 PyObject *operand2_object = operand2;
574
575 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
576 assert(r != Py_NotImplemented);
577
578 obj_result = r;
579 goto exit_result_object;
580 }
581
582 exit_result_ok_cfloat:
583 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
584 goto exit_result_ok;
585
586 exit_result_object:
587 if (unlikely(obj_result == NULL)) {
588 goto exit_result_exception;
589 }
590 result = obj_result;
591 goto exit_result_ok;
592
593 exit_result_ok_const_float_0_0:
594 Py_INCREF(const_float_0_0);
595 result = const_float_0_0;
596 goto exit_result_ok;
597
598 exit_result_ok_const_float_minus_0_0:
599 Py_INCREF(const_float_minus_0_0);
600 result = const_float_minus_0_0;
601 goto exit_result_ok;
602
603 exit_result_ok:
604 return result;
605
606 exit_result_exception:
607 return NULL;
608 }
609
610 return __BINARY_OPERATION_TRUEDIV_OBJECT_INT_OBJECT(operand1, operand2);
611}
612
613PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_INT_OBJECT(PyObject *operand1, PyObject *operand2) {
614 return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_OBJECT(operand1, operand2);
615}
616#endif
617
618/* Code referring to "LONG" corresponds to Python2 'long', Python3 'int' and "LONG" to Python2 'long', Python3 'int'. */
619static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_LONG_LONG(PyObject *operand1, PyObject *operand2) {
620 CHECK_OBJECT(operand1);
621 assert(PyLong_CheckExact(operand1));
622 CHECK_OBJECT(operand2);
623 assert(PyLong_CheckExact(operand2));
624
625 PyObject *result;
626
627 // Not every code path will make use of all possible results.
628#if defined(_MSC_VER)
629#pragma warning(push)
630#pragma warning(disable : 4101)
631#endif
632 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
633 NUITKA_MAY_BE_UNUSED long clong_result;
634#if defined(_MSC_VER)
635#pragma warning(pop)
636#endif
637
638 PyObject *x = PyLong_Type.tp_as_number->nb_true_divide(operand1, operand2);
639 assert(x != Py_NotImplemented);
640
641 obj_result = x;
642 goto exit_result_object;
643
644exit_result_object:
645 if (unlikely(obj_result == NULL)) {
646 goto exit_result_exception;
647 }
648 result = obj_result;
649 goto exit_result_ok;
650
651exit_result_ok:
652 return result;
653
654exit_result_exception:
655 return NULL;
656}
657
658PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_LONG_LONG(PyObject *operand1, PyObject *operand2) {
659 return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_LONG(operand1, operand2);
660}
661
662/* Code referring to "OBJECT" corresponds to any Python object and "LONG" to Python2 'long', Python3 'int'. */
663static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_LONG(PyObject *operand1,
664 PyObject *operand2) {
665 PyTypeObject *type1 = Py_TYPE(operand1);
666
667#if defined(_MSC_VER)
668#pragma warning(push)
669#pragma warning(disable : 4101)
670#endif
671 NUITKA_MAY_BE_UNUSED bool cbool_result;
672 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
673#if defined(_MSC_VER)
674#pragma warning(pop)
675#endif
676
677 binaryfunc slot1 =
678 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_true_divide : NULL;
679 binaryfunc slot2 = NULL;
680
681 if (!(type1 == &PyLong_Type)) {
682 // Different types, need to consider second value slot.
683
684 slot2 = PyLong_Type.tp_as_number->nb_true_divide;
685
686 if (slot1 == slot2) {
687 slot2 = NULL;
688 }
689 }
690
691 if (slot1 != NULL) {
692 PyObject *x = slot1(operand1, operand2);
693
694 if (x != Py_NotImplemented) {
695 obj_result = x;
696 goto exit_binary_result_object;
697 }
698
699 Py_DECREF_IMMORTAL(x);
700 }
701
702 if (slot2 != NULL) {
703 PyObject *x = slot2(operand1, operand2);
704
705 if (x != Py_NotImplemented) {
706 obj_result = x;
707 goto exit_binary_result_object;
708 }
709
710 Py_DECREF_IMMORTAL(x);
711 }
712
713#if PYTHON_VERSION < 0x300
714 if (!NEW_STYLE_NUMBER_TYPE(type1) || !1) {
715 coercion c1 =
716 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_coerce : NULL;
717
718 if (c1 != NULL) {
719 PyObject *coerced1 = operand1;
720 PyObject *coerced2 = operand2;
721
722 int err = c1(&coerced1, &coerced2);
723
724 if (unlikely(err < 0)) {
725 goto exit_binary_exception;
726 }
727
728 if (err == 0) {
729 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
730
731 if (likely(mv == NULL)) {
732 binaryfunc slot = mv->nb_true_divide;
733
734 if (likely(slot != NULL)) {
735 PyObject *x = slot(coerced1, coerced2);
736
737 Py_DECREF(coerced1);
738 Py_DECREF(coerced2);
739
740 obj_result = x;
741 goto exit_binary_result_object;
742 }
743 }
744
745 // nb_coerce took a reference.
746 Py_DECREF(coerced1);
747 Py_DECREF(coerced2);
748 }
749 }
750 coercion c2 = PyLong_Type.tp_as_number->nb_coerce;
751
752 if (c2 != NULL) {
753 PyObject *coerced1 = operand1;
754 PyObject *coerced2 = operand2;
755
756 int err = c2(&coerced2, &coerced1);
757
758 if (unlikely(err < 0)) {
759 goto exit_binary_exception;
760 }
761
762 if (err == 0) {
763 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
764
765 if (likely(mv == NULL)) {
766 binaryfunc slot = mv->nb_true_divide;
767
768 if (likely(slot != NULL)) {
769 PyObject *x = slot(coerced1, coerced2);
770
771 Py_DECREF(coerced1);
772 Py_DECREF(coerced2);
773
774 obj_result = x;
775 goto exit_binary_result_object;
776 }
777 }
778
779 // nb_coerce took a reference.
780 Py_DECREF(coerced1);
781 Py_DECREF(coerced2);
782 }
783 }
784 }
785#endif
786
787#if PYTHON_VERSION < 0x300
788 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: '%s' and 'long'", type1->tp_name);
789#else
790 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: '%s' and 'int'", type1->tp_name);
791#endif
792 goto exit_binary_exception;
793
794exit_binary_result_object:
795 return obj_result;
796
797exit_binary_exception:
798 return NULL;
799}
800static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_LONG(PyObject *operand1, PyObject *operand2) {
801 CHECK_OBJECT(operand1);
802 CHECK_OBJECT(operand2);
803 assert(PyLong_CheckExact(operand2));
804
805 PyTypeObject *type1 = Py_TYPE(operand1);
806
807 if (type1 == &PyLong_Type) {
808 PyObject *result;
809
810 // return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_LONG(operand1, operand2);
811
812 // Not every code path will make use of all possible results.
813#if defined(_MSC_VER)
814#pragma warning(push)
815#pragma warning(disable : 4101)
816#endif
817 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
818 NUITKA_MAY_BE_UNUSED long clong_result;
819#if defined(_MSC_VER)
820#pragma warning(pop)
821#endif
822
823 PyObject *x = PyLong_Type.tp_as_number->nb_true_divide(operand1, operand2);
824 assert(x != Py_NotImplemented);
825
826 obj_result = x;
827 goto exit_result_object;
828
829 exit_result_object:
830 if (unlikely(obj_result == NULL)) {
831 goto exit_result_exception;
832 }
833 result = obj_result;
834 goto exit_result_ok;
835
836 exit_result_ok:
837 return result;
838
839 exit_result_exception:
840 return NULL;
841 }
842
843 return __BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_LONG(operand1, operand2);
844}
845
846PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_LONG(PyObject *operand1, PyObject *operand2) {
847 return _BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_LONG(operand1, operand2);
848}
849
850/* Code referring to "LONG" corresponds to Python2 'long', Python3 'int' and "OBJECT" to any Python object. */
851static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_LONG_OBJECT(PyObject *operand1,
852 PyObject *operand2) {
853 PyTypeObject *type2 = Py_TYPE(operand2);
854
855#if defined(_MSC_VER)
856#pragma warning(push)
857#pragma warning(disable : 4101)
858#endif
859 NUITKA_MAY_BE_UNUSED bool cbool_result;
860 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
861#if defined(_MSC_VER)
862#pragma warning(pop)
863#endif
864
865 binaryfunc slot1 = PyLong_Type.tp_as_number->nb_true_divide;
866 binaryfunc slot2 = NULL;
867
868 if (!(&PyLong_Type == type2)) {
869 // Different types, need to consider second value slot.
870
871 slot2 =
872 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_true_divide : NULL;
873
874 if (slot1 == slot2) {
875 slot2 = NULL;
876 }
877 }
878
879 if (slot1 != NULL) {
880 if (slot2 != NULL) {
881 if (Nuitka_Type_IsSubtype(type2, &PyLong_Type)) {
882 PyObject *x = slot2(operand1, operand2);
883
884 if (x != Py_NotImplemented) {
885 obj_result = x;
886 goto exit_binary_result_object;
887 }
888
889 Py_DECREF_IMMORTAL(x);
890 slot2 = NULL;
891 }
892 }
893
894 PyObject *x = slot1(operand1, operand2);
895
896 if (x != Py_NotImplemented) {
897 obj_result = x;
898 goto exit_binary_result_object;
899 }
900
901 Py_DECREF_IMMORTAL(x);
902 }
903
904 if (slot2 != NULL) {
905 PyObject *x = slot2(operand1, operand2);
906
907 if (x != Py_NotImplemented) {
908 obj_result = x;
909 goto exit_binary_result_object;
910 }
911
912 Py_DECREF_IMMORTAL(x);
913 }
914
915#if PYTHON_VERSION < 0x300
916 if (!1 || !NEW_STYLE_NUMBER_TYPE(type2)) {
917 coercion c1 = PyLong_Type.tp_as_number->nb_coerce;
918
919 if (c1 != NULL) {
920 PyObject *coerced1 = operand1;
921 PyObject *coerced2 = operand2;
922
923 int err = c1(&coerced1, &coerced2);
924
925 if (unlikely(err < 0)) {
926 goto exit_binary_exception;
927 }
928
929 if (err == 0) {
930 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
931
932 if (likely(mv == NULL)) {
933 binaryfunc slot = mv->nb_true_divide;
934
935 if (likely(slot != NULL)) {
936 PyObject *x = slot(coerced1, coerced2);
937
938 Py_DECREF(coerced1);
939 Py_DECREF(coerced2);
940
941 obj_result = x;
942 goto exit_binary_result_object;
943 }
944 }
945
946 // nb_coerce took a reference.
947 Py_DECREF(coerced1);
948 Py_DECREF(coerced2);
949 }
950 }
951 coercion c2 =
952 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_coerce : NULL;
953
954 if (c2 != NULL) {
955 PyObject *coerced1 = operand1;
956 PyObject *coerced2 = operand2;
957
958 int err = c2(&coerced2, &coerced1);
959
960 if (unlikely(err < 0)) {
961 goto exit_binary_exception;
962 }
963
964 if (err == 0) {
965 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
966
967 if (likely(mv == NULL)) {
968 binaryfunc slot = mv->nb_true_divide;
969
970 if (likely(slot != NULL)) {
971 PyObject *x = slot(coerced1, coerced2);
972
973 Py_DECREF(coerced1);
974 Py_DECREF(coerced2);
975
976 obj_result = x;
977 goto exit_binary_result_object;
978 }
979 }
980
981 // nb_coerce took a reference.
982 Py_DECREF(coerced1);
983 Py_DECREF(coerced2);
984 }
985 }
986 }
987#endif
988
989#if PYTHON_VERSION < 0x300
990 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'long' and '%s'", type2->tp_name);
991#else
992 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'int' and '%s'", type2->tp_name);
993#endif
994 goto exit_binary_exception;
995
996exit_binary_result_object:
997 return obj_result;
998
999exit_binary_exception:
1000 return NULL;
1001}
1002static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_LONG_OBJECT(PyObject *operand1, PyObject *operand2) {
1003 CHECK_OBJECT(operand1);
1004 assert(PyLong_CheckExact(operand1));
1005 CHECK_OBJECT(operand2);
1006
1007 PyTypeObject *type2 = Py_TYPE(operand2);
1008
1009 if (&PyLong_Type == type2) {
1010 PyObject *result;
1011
1012 // return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_LONG(operand1, operand2);
1013
1014 // Not every code path will make use of all possible results.
1015#if defined(_MSC_VER)
1016#pragma warning(push)
1017#pragma warning(disable : 4101)
1018#endif
1019 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1020 NUITKA_MAY_BE_UNUSED long clong_result;
1021#if defined(_MSC_VER)
1022#pragma warning(pop)
1023#endif
1024
1025 PyObject *x = PyLong_Type.tp_as_number->nb_true_divide(operand1, operand2);
1026 assert(x != Py_NotImplemented);
1027
1028 obj_result = x;
1029 goto exit_result_object;
1030
1031 exit_result_object:
1032 if (unlikely(obj_result == NULL)) {
1033 goto exit_result_exception;
1034 }
1035 result = obj_result;
1036 goto exit_result_ok;
1037
1038 exit_result_ok:
1039 return result;
1040
1041 exit_result_exception:
1042 return NULL;
1043 }
1044
1045 return __BINARY_OPERATION_TRUEDIV_OBJECT_LONG_OBJECT(operand1, operand2);
1046}
1047
1048PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_LONG_OBJECT(PyObject *operand1, PyObject *operand2) {
1049 return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_OBJECT(operand1, operand2);
1050}
1051
1052/* Code referring to "FLOAT" corresponds to Python 'float' and "FLOAT" to Python 'float'. */
1053static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_FLOAT(PyObject *operand1, PyObject *operand2) {
1054 CHECK_OBJECT(operand1);
1055 assert(PyFloat_CheckExact(operand1));
1056 CHECK_OBJECT(operand2);
1057 assert(PyFloat_CheckExact(operand2));
1058
1059 PyObject *result;
1060
1061#if defined(_MSC_VER)
1062#pragma warning(push)
1063#pragma warning(disable : 4101)
1064#endif
1065 // Not every code path will make use of all possible results.
1066 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1067 NUITKA_MAY_BE_UNUSED long clong_result;
1068 NUITKA_MAY_BE_UNUSED double cfloat_result;
1069#if defined(_MSC_VER)
1070#pragma warning(pop)
1071#endif
1072
1073 CHECK_OBJECT(operand1);
1074 assert(PyFloat_CheckExact(operand1));
1075 CHECK_OBJECT(operand2);
1076 assert(PyFloat_CheckExact(operand2));
1077
1078 const double a = PyFloat_AS_DOUBLE(operand1);
1079 const double b = PyFloat_AS_DOUBLE(operand2);
1080
1081 if (unlikely(b == 0.0)) {
1082 PyThreadState *tstate = PyThreadState_GET();
1083
1084 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "float division by zero");
1085 goto exit_result_exception;
1086 }
1087
1088 {
1089 double r = a / b;
1090
1091 cfloat_result = r;
1092 goto exit_result_ok_cfloat;
1093 }
1094
1095exit_result_ok_cfloat:
1096 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
1097 goto exit_result_ok;
1098
1099exit_result_ok:
1100 return result;
1101
1102exit_result_exception:
1103 return NULL;
1104}
1105
1106PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_FLOAT(PyObject *operand1, PyObject *operand2) {
1107 return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_FLOAT(operand1, operand2);
1108}
1109
1110/* Code referring to "OBJECT" corresponds to any Python object and "FLOAT" to Python 'float'. */
1111static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_FLOAT(PyObject *operand1,
1112 PyObject *operand2) {
1113 PyTypeObject *type1 = Py_TYPE(operand1);
1114
1115#if defined(_MSC_VER)
1116#pragma warning(push)
1117#pragma warning(disable : 4101)
1118#endif
1119 NUITKA_MAY_BE_UNUSED bool cbool_result;
1120 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1121#if defined(_MSC_VER)
1122#pragma warning(pop)
1123#endif
1124
1125 binaryfunc slot1 =
1126 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_true_divide : NULL;
1127 binaryfunc slot2 = NULL;
1128
1129 if (!(type1 == &PyFloat_Type)) {
1130 // Different types, need to consider second value slot.
1131
1132 slot2 = PyFloat_Type.tp_as_number->nb_true_divide;
1133
1134 if (slot1 == slot2) {
1135 slot2 = NULL;
1136 }
1137 }
1138
1139 if (slot1 != NULL) {
1140 PyObject *x = slot1(operand1, operand2);
1141
1142 if (x != Py_NotImplemented) {
1143 obj_result = x;
1144 goto exit_binary_result_object;
1145 }
1146
1147 Py_DECREF_IMMORTAL(x);
1148 }
1149
1150 if (slot2 != NULL) {
1151 PyObject *x = slot2(operand1, operand2);
1152
1153 if (x != Py_NotImplemented) {
1154 obj_result = x;
1155 goto exit_binary_result_object;
1156 }
1157
1158 Py_DECREF_IMMORTAL(x);
1159 }
1160
1161#if PYTHON_VERSION < 0x300
1162 if (!NEW_STYLE_NUMBER_TYPE(type1) || !1) {
1163 coercion c1 =
1164 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_coerce : NULL;
1165
1166 if (c1 != NULL) {
1167 PyObject *coerced1 = operand1;
1168 PyObject *coerced2 = operand2;
1169
1170 int err = c1(&coerced1, &coerced2);
1171
1172 if (unlikely(err < 0)) {
1173 goto exit_binary_exception;
1174 }
1175
1176 if (err == 0) {
1177 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
1178
1179 if (likely(mv == NULL)) {
1180 binaryfunc slot = mv->nb_true_divide;
1181
1182 if (likely(slot != NULL)) {
1183 PyObject *x = slot(coerced1, coerced2);
1184
1185 Py_DECREF(coerced1);
1186 Py_DECREF(coerced2);
1187
1188 obj_result = x;
1189 goto exit_binary_result_object;
1190 }
1191 }
1192
1193 // nb_coerce took a reference.
1194 Py_DECREF(coerced1);
1195 Py_DECREF(coerced2);
1196 }
1197 }
1198 coercion c2 = PyFloat_Type.tp_as_number->nb_coerce;
1199
1200 if (c2 != NULL) {
1201 PyObject *coerced1 = operand1;
1202 PyObject *coerced2 = operand2;
1203
1204 int err = c2(&coerced2, &coerced1);
1205
1206 if (unlikely(err < 0)) {
1207 goto exit_binary_exception;
1208 }
1209
1210 if (err == 0) {
1211 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
1212
1213 if (likely(mv == NULL)) {
1214 binaryfunc slot = mv->nb_true_divide;
1215
1216 if (likely(slot != NULL)) {
1217 PyObject *x = slot(coerced1, coerced2);
1218
1219 Py_DECREF(coerced1);
1220 Py_DECREF(coerced2);
1221
1222 obj_result = x;
1223 goto exit_binary_result_object;
1224 }
1225 }
1226
1227 // nb_coerce took a reference.
1228 Py_DECREF(coerced1);
1229 Py_DECREF(coerced2);
1230 }
1231 }
1232 }
1233#endif
1234
1235 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: '%s' and 'float'", type1->tp_name);
1236 goto exit_binary_exception;
1237
1238exit_binary_result_object:
1239 return obj_result;
1240
1241exit_binary_exception:
1242 return NULL;
1243}
1244static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_FLOAT(PyObject *operand1, PyObject *operand2) {
1245 CHECK_OBJECT(operand1);
1246 CHECK_OBJECT(operand2);
1247 assert(PyFloat_CheckExact(operand2));
1248
1249 PyTypeObject *type1 = Py_TYPE(operand1);
1250
1251 if (type1 == &PyFloat_Type) {
1252 PyObject *result;
1253
1254 // return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_FLOAT(operand1, operand2);
1255
1256#if defined(_MSC_VER)
1257#pragma warning(push)
1258#pragma warning(disable : 4101)
1259#endif
1260 // Not every code path will make use of all possible results.
1261 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1262 NUITKA_MAY_BE_UNUSED long clong_result;
1263 NUITKA_MAY_BE_UNUSED double cfloat_result;
1264#if defined(_MSC_VER)
1265#pragma warning(pop)
1266#endif
1267
1268 CHECK_OBJECT(operand1);
1269 assert(PyFloat_CheckExact(operand1));
1270 CHECK_OBJECT(operand2);
1271 assert(PyFloat_CheckExact(operand2));
1272
1273 const double a = PyFloat_AS_DOUBLE(operand1);
1274 const double b = PyFloat_AS_DOUBLE(operand2);
1275
1276 if (unlikely(b == 0.0)) {
1277 PyThreadState *tstate = PyThreadState_GET();
1278
1279 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "float division by zero");
1280 goto exit_result_exception;
1281 }
1282
1283 {
1284 double r = a / b;
1285
1286 cfloat_result = r;
1287 goto exit_result_ok_cfloat;
1288 }
1289
1290 exit_result_ok_cfloat:
1291 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
1292 goto exit_result_ok;
1293
1294 exit_result_ok:
1295 return result;
1296
1297 exit_result_exception:
1298 return NULL;
1299 }
1300
1301 return __BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_FLOAT(operand1, operand2);
1302}
1303
1304PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_FLOAT(PyObject *operand1, PyObject *operand2) {
1305 return _BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_FLOAT(operand1, operand2);
1306}
1307
1308/* Code referring to "FLOAT" corresponds to Python 'float' and "OBJECT" to any Python object. */
1309static HEDLEY_NEVER_INLINE PyObject *__BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_OBJECT(PyObject *operand1,
1310 PyObject *operand2) {
1311 PyTypeObject *type2 = Py_TYPE(operand2);
1312
1313#if defined(_MSC_VER)
1314#pragma warning(push)
1315#pragma warning(disable : 4101)
1316#endif
1317 NUITKA_MAY_BE_UNUSED bool cbool_result;
1318 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1319#if defined(_MSC_VER)
1320#pragma warning(pop)
1321#endif
1322
1323 binaryfunc slot1 = PyFloat_Type.tp_as_number->nb_true_divide;
1324 binaryfunc slot2 = NULL;
1325
1326 if (!(&PyFloat_Type == type2)) {
1327 // Different types, need to consider second value slot.
1328
1329 slot2 =
1330 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_true_divide : NULL;
1331
1332 if (slot1 == slot2) {
1333 slot2 = NULL;
1334 }
1335 }
1336
1337 if (slot1 != NULL) {
1338 if (slot2 != NULL) {
1339 if (Nuitka_Type_IsSubtype(type2, &PyFloat_Type)) {
1340 PyObject *x = slot2(operand1, operand2);
1341
1342 if (x != Py_NotImplemented) {
1343 obj_result = x;
1344 goto exit_binary_result_object;
1345 }
1346
1347 Py_DECREF_IMMORTAL(x);
1348 slot2 = NULL;
1349 }
1350 }
1351
1352 PyObject *x = slot1(operand1, operand2);
1353
1354 if (x != Py_NotImplemented) {
1355 obj_result = x;
1356 goto exit_binary_result_object;
1357 }
1358
1359 Py_DECREF_IMMORTAL(x);
1360 }
1361
1362 if (slot2 != NULL) {
1363 PyObject *x = slot2(operand1, operand2);
1364
1365 if (x != Py_NotImplemented) {
1366 obj_result = x;
1367 goto exit_binary_result_object;
1368 }
1369
1370 Py_DECREF_IMMORTAL(x);
1371 }
1372
1373#if PYTHON_VERSION < 0x300
1374 if (!1 || !NEW_STYLE_NUMBER_TYPE(type2)) {
1375 coercion c1 = PyFloat_Type.tp_as_number->nb_coerce;
1376
1377 if (c1 != NULL) {
1378 PyObject *coerced1 = operand1;
1379 PyObject *coerced2 = operand2;
1380
1381 int err = c1(&coerced1, &coerced2);
1382
1383 if (unlikely(err < 0)) {
1384 goto exit_binary_exception;
1385 }
1386
1387 if (err == 0) {
1388 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
1389
1390 if (likely(mv == NULL)) {
1391 binaryfunc slot = mv->nb_true_divide;
1392
1393 if (likely(slot != NULL)) {
1394 PyObject *x = slot(coerced1, coerced2);
1395
1396 Py_DECREF(coerced1);
1397 Py_DECREF(coerced2);
1398
1399 obj_result = x;
1400 goto exit_binary_result_object;
1401 }
1402 }
1403
1404 // nb_coerce took a reference.
1405 Py_DECREF(coerced1);
1406 Py_DECREF(coerced2);
1407 }
1408 }
1409 coercion c2 =
1410 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_coerce : NULL;
1411
1412 if (c2 != NULL) {
1413 PyObject *coerced1 = operand1;
1414 PyObject *coerced2 = operand2;
1415
1416 int err = c2(&coerced2, &coerced1);
1417
1418 if (unlikely(err < 0)) {
1419 goto exit_binary_exception;
1420 }
1421
1422 if (err == 0) {
1423 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
1424
1425 if (likely(mv == NULL)) {
1426 binaryfunc slot = mv->nb_true_divide;
1427
1428 if (likely(slot != NULL)) {
1429 PyObject *x = slot(coerced1, coerced2);
1430
1431 Py_DECREF(coerced1);
1432 Py_DECREF(coerced2);
1433
1434 obj_result = x;
1435 goto exit_binary_result_object;
1436 }
1437 }
1438
1439 // nb_coerce took a reference.
1440 Py_DECREF(coerced1);
1441 Py_DECREF(coerced2);
1442 }
1443 }
1444 }
1445#endif
1446
1447 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'float' and '%s'", type2->tp_name);
1448 goto exit_binary_exception;
1449
1450exit_binary_result_object:
1451 return obj_result;
1452
1453exit_binary_exception:
1454 return NULL;
1455}
1456static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_OBJECT(PyObject *operand1, PyObject *operand2) {
1457 CHECK_OBJECT(operand1);
1458 assert(PyFloat_CheckExact(operand1));
1459 CHECK_OBJECT(operand2);
1460
1461 PyTypeObject *type2 = Py_TYPE(operand2);
1462
1463 if (&PyFloat_Type == type2) {
1464 PyObject *result;
1465
1466 // return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_FLOAT(operand1, operand2);
1467
1468#if defined(_MSC_VER)
1469#pragma warning(push)
1470#pragma warning(disable : 4101)
1471#endif
1472 // Not every code path will make use of all possible results.
1473 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1474 NUITKA_MAY_BE_UNUSED long clong_result;
1475 NUITKA_MAY_BE_UNUSED double cfloat_result;
1476#if defined(_MSC_VER)
1477#pragma warning(pop)
1478#endif
1479
1480 CHECK_OBJECT(operand1);
1481 assert(PyFloat_CheckExact(operand1));
1482 CHECK_OBJECT(operand2);
1483 assert(PyFloat_CheckExact(operand2));
1484
1485 const double a = PyFloat_AS_DOUBLE(operand1);
1486 const double b = PyFloat_AS_DOUBLE(operand2);
1487
1488 if (unlikely(b == 0.0)) {
1489 PyThreadState *tstate = PyThreadState_GET();
1490
1491 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "float division by zero");
1492 goto exit_result_exception;
1493 }
1494
1495 {
1496 double r = a / b;
1497
1498 cfloat_result = r;
1499 goto exit_result_ok_cfloat;
1500 }
1501
1502 exit_result_ok_cfloat:
1503 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
1504 goto exit_result_ok;
1505
1506 exit_result_ok:
1507 return result;
1508
1509 exit_result_exception:
1510 return NULL;
1511 }
1512
1513 return __BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_OBJECT(operand1, operand2);
1514}
1515
1516PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_OBJECT(PyObject *operand1, PyObject *operand2) {
1517 return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_OBJECT(operand1, operand2);
1518}
1519
1520/* Code referring to "FLOAT" corresponds to Python 'float' and "LONG" to Python2 'long', Python3 'int'. */
1521static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_LONG(PyObject *operand1, PyObject *operand2) {
1522 CHECK_OBJECT(operand1);
1523 assert(PyFloat_CheckExact(operand1));
1524 CHECK_OBJECT(operand2);
1525 assert(PyLong_CheckExact(operand2));
1526
1527#if defined(_MSC_VER)
1528#pragma warning(push)
1529#pragma warning(disable : 4101)
1530#endif
1531 NUITKA_MAY_BE_UNUSED bool cbool_result;
1532 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1533#if defined(_MSC_VER)
1534#pragma warning(pop)
1535#endif
1536
1537 binaryfunc slot1 = PyFloat_Type.tp_as_number->nb_true_divide;
1538 // Slot2 ignored on purpose, type1 takes precedence.
1539
1540 if (slot1 != NULL) {
1541 PyObject *x = slot1(operand1, operand2);
1542
1543 if (x != Py_NotImplemented) {
1544 obj_result = x;
1545 goto exit_binary_result_object;
1546 }
1547
1548 Py_DECREF_IMMORTAL(x);
1549 }
1550
1551 // Statically recognized that coercion is not possible with these types
1552
1553#if PYTHON_VERSION < 0x300
1554 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'float' and 'long'");
1555#else
1556 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'float' and 'int'");
1557#endif
1558 goto exit_binary_exception;
1559
1560exit_binary_result_object:
1561 return obj_result;
1562
1563exit_binary_exception:
1564 return NULL;
1565}
1566
1567PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_LONG(PyObject *operand1, PyObject *operand2) {
1568 return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_LONG(operand1, operand2);
1569}
1570
1571/* Code referring to "LONG" corresponds to Python2 'long', Python3 'int' and "FLOAT" to Python 'float'. */
1572static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_LONG_FLOAT(PyObject *operand1, PyObject *operand2) {
1573 CHECK_OBJECT(operand1);
1574 assert(PyLong_CheckExact(operand1));
1575 CHECK_OBJECT(operand2);
1576 assert(PyFloat_CheckExact(operand2));
1577
1578#if defined(_MSC_VER)
1579#pragma warning(push)
1580#pragma warning(disable : 4101)
1581#endif
1582 NUITKA_MAY_BE_UNUSED bool cbool_result;
1583 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1584#if defined(_MSC_VER)
1585#pragma warning(pop)
1586#endif
1587
1588 // Slot1 ignored on purpose, type2 takes precedence.
1589 binaryfunc slot2 = NULL;
1590
1591 if (!(0)) {
1592 // Different types, need to consider second value slot.
1593
1594 slot2 = PyFloat_Type.tp_as_number->nb_true_divide;
1595 }
1596
1597 if (slot2 != NULL) {
1598 PyObject *x = slot2(operand1, operand2);
1599
1600 if (x != Py_NotImplemented) {
1601 obj_result = x;
1602 goto exit_binary_result_object;
1603 }
1604
1605 Py_DECREF_IMMORTAL(x);
1606 }
1607
1608 // Statically recognized that coercion is not possible with these types
1609
1610#if PYTHON_VERSION < 0x300
1611 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'long' and 'float'");
1612#else
1613 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'int' and 'float'");
1614#endif
1615 goto exit_binary_exception;
1616
1617exit_binary_result_object:
1618 return obj_result;
1619
1620exit_binary_exception:
1621 return NULL;
1622}
1623
1624PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_LONG_FLOAT(PyObject *operand1, PyObject *operand2) {
1625 return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_FLOAT(operand1, operand2);
1626}
1627
1628#if PYTHON_VERSION < 0x300
1629/* Code referring to "FLOAT" corresponds to Python 'float' and "INT" to Python2 'int'. */
1630static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_INT(PyObject *operand1, PyObject *operand2) {
1631 CHECK_OBJECT(operand1);
1632 assert(PyFloat_CheckExact(operand1));
1633 CHECK_OBJECT(operand2);
1634 assert(PyInt_CheckExact(operand2));
1635
1636#if defined(_MSC_VER)
1637#pragma warning(push)
1638#pragma warning(disable : 4101)
1639#endif
1640 NUITKA_MAY_BE_UNUSED bool cbool_result;
1641 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1642#if defined(_MSC_VER)
1643#pragma warning(pop)
1644#endif
1645
1646 binaryfunc slot1 = PyFloat_Type.tp_as_number->nb_true_divide;
1647 // Slot2 ignored on purpose, type1 takes precedence.
1648
1649 if (slot1 != NULL) {
1650 PyObject *x = slot1(operand1, operand2);
1651
1652 if (x != Py_NotImplemented) {
1653 obj_result = x;
1654 goto exit_binary_result_object;
1655 }
1656
1657 Py_DECREF_IMMORTAL(x);
1658 }
1659
1660 // Statically recognized that coercion is not possible with these types
1661
1662 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'float' and 'int'");
1663 goto exit_binary_exception;
1664
1665exit_binary_result_object:
1666 return obj_result;
1667
1668exit_binary_exception:
1669 return NULL;
1670}
1671
1672PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_INT(PyObject *operand1, PyObject *operand2) {
1673 return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_INT(operand1, operand2);
1674}
1675#endif
1676
1677#if PYTHON_VERSION < 0x300
1678/* Code referring to "INT" corresponds to Python2 'int' and "FLOAT" to Python 'float'. */
1679static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_INT_FLOAT(PyObject *operand1, PyObject *operand2) {
1680 CHECK_OBJECT(operand1);
1681 assert(PyInt_CheckExact(operand1));
1682 CHECK_OBJECT(operand2);
1683 assert(PyFloat_CheckExact(operand2));
1684
1685#if defined(_MSC_VER)
1686#pragma warning(push)
1687#pragma warning(disable : 4101)
1688#endif
1689 NUITKA_MAY_BE_UNUSED bool cbool_result;
1690 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1691#if defined(_MSC_VER)
1692#pragma warning(pop)
1693#endif
1694
1695 // Slot1 ignored on purpose, type2 takes precedence.
1696 binaryfunc slot2 = NULL;
1697
1698 if (!(0)) {
1699 // Different types, need to consider second value slot.
1700
1701 slot2 = PyFloat_Type.tp_as_number->nb_true_divide;
1702 }
1703
1704 if (slot2 != NULL) {
1705 PyObject *x = slot2(operand1, operand2);
1706
1707 if (x != Py_NotImplemented) {
1708 obj_result = x;
1709 goto exit_binary_result_object;
1710 }
1711
1712 Py_DECREF_IMMORTAL(x);
1713 }
1714
1715 // Statically recognized that coercion is not possible with these types
1716
1717 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'int' and 'float'");
1718 goto exit_binary_exception;
1719
1720exit_binary_result_object:
1721 return obj_result;
1722
1723exit_binary_exception:
1724 return NULL;
1725}
1726
1727PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_INT_FLOAT(PyObject *operand1, PyObject *operand2) {
1728 return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_FLOAT(operand1, operand2);
1729}
1730#endif
1731
1732#if PYTHON_VERSION < 0x300
1733/* Code referring to "LONG" corresponds to Python2 'long', Python3 'int' and "INT" to Python2 'int'. */
1734static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_LONG_INT(PyObject *operand1, PyObject *operand2) {
1735 CHECK_OBJECT(operand1);
1736 assert(PyLong_CheckExact(operand1));
1737 CHECK_OBJECT(operand2);
1738 assert(PyInt_CheckExact(operand2));
1739
1740#if defined(_MSC_VER)
1741#pragma warning(push)
1742#pragma warning(disable : 4101)
1743#endif
1744 NUITKA_MAY_BE_UNUSED bool cbool_result;
1745 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1746#if defined(_MSC_VER)
1747#pragma warning(pop)
1748#endif
1749
1750 binaryfunc slot1 = PyLong_Type.tp_as_number->nb_true_divide;
1751 // Slot2 ignored on purpose, type1 takes precedence.
1752
1753 if (slot1 != NULL) {
1754 PyObject *x = slot1(operand1, operand2);
1755
1756 if (x != Py_NotImplemented) {
1757 obj_result = x;
1758 goto exit_binary_result_object;
1759 }
1760
1761 Py_DECREF_IMMORTAL(x);
1762 }
1763
1764 // Statically recognized that coercion is not possible with these types
1765
1766 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'long' and 'int'");
1767 goto exit_binary_exception;
1768
1769exit_binary_result_object:
1770 return obj_result;
1771
1772exit_binary_exception:
1773 return NULL;
1774}
1775
1776PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_LONG_INT(PyObject *operand1, PyObject *operand2) {
1777 return _BINARY_OPERATION_TRUEDIV_OBJECT_LONG_INT(operand1, operand2);
1778}
1779#endif
1780
1781#if PYTHON_VERSION < 0x300
1782/* Code referring to "INT" corresponds to Python2 'int' and "LONG" to Python2 'long', Python3 'int'. */
1783static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_INT_LONG(PyObject *operand1, PyObject *operand2) {
1784 CHECK_OBJECT(operand1);
1785 assert(PyInt_CheckExact(operand1));
1786 CHECK_OBJECT(operand2);
1787 assert(PyLong_CheckExact(operand2));
1788
1789#if defined(_MSC_VER)
1790#pragma warning(push)
1791#pragma warning(disable : 4101)
1792#endif
1793 NUITKA_MAY_BE_UNUSED bool cbool_result;
1794 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1795#if defined(_MSC_VER)
1796#pragma warning(pop)
1797#endif
1798
1799 // Slot1 ignored on purpose, type2 takes precedence.
1800 binaryfunc slot2 = NULL;
1801
1802 if (!(0)) {
1803 // Different types, need to consider second value slot.
1804
1805 slot2 = PyLong_Type.tp_as_number->nb_true_divide;
1806 }
1807
1808 if (slot2 != NULL) {
1809 PyObject *x = slot2(operand1, operand2);
1810
1811 if (x != Py_NotImplemented) {
1812 obj_result = x;
1813 goto exit_binary_result_object;
1814 }
1815
1816 Py_DECREF_IMMORTAL(x);
1817 }
1818
1819 // Statically recognized that coercion is not possible with these types
1820
1821 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: 'int' and 'long'");
1822 goto exit_binary_exception;
1823
1824exit_binary_result_object:
1825 return obj_result;
1826
1827exit_binary_exception:
1828 return NULL;
1829}
1830
1831PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_INT_LONG(PyObject *operand1, PyObject *operand2) {
1832 return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_LONG(operand1, operand2);
1833}
1834#endif
1835
1836#if PYTHON_VERSION < 0x300
1837/* Code referring to "INT" corresponds to Python2 'int' and "CLONG" to C platform long value. */
1838static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_INT_CLONG(PyObject *operand1, long operand2) {
1839 CHECK_OBJECT(operand1);
1840 assert(PyInt_CheckExact(operand1));
1841
1842 PyObject *result;
1843
1844 // Not every code path will make use of all possible results.
1845#if defined(_MSC_VER)
1846#pragma warning(push)
1847#pragma warning(disable : 4101)
1848#endif
1849 NUITKA_MAY_BE_UNUSED bool cbool_result;
1850 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1851 NUITKA_MAY_BE_UNUSED long clong_result;
1852 NUITKA_MAY_BE_UNUSED double cfloat_result;
1853#if defined(_MSC_VER)
1854#pragma warning(pop)
1855#endif
1856
1857 CHECK_OBJECT(operand1);
1858 assert(PyInt_CheckExact(operand1));
1859
1860 const long a = PyInt_AS_LONG(operand1);
1861 const long b = operand2;
1862
1863 if (unlikely(b == 0)) {
1864 PyThreadState *tstate = PyThreadState_GET();
1865
1866 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
1867 goto exit_result_exception;
1868 }
1869
1870 if (a == 0) {
1871 if (b < 0) {
1872 goto exit_result_ok_const_float_minus_0_0;
1873 } else {
1874 goto exit_result_ok_const_float_0_0;
1875 }
1876 }
1877
1878/* May need to resort to LONG code, which we currently do not
1879 * specialize yet. TODO: Once we do that, call it here instead.
1880 */
1881#if DBL_MANT_DIG < WIDTH_OF_ULONG
1882 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
1883 } else
1884#endif
1885 {
1886 double r = (double)a / (double)b;
1887
1888 cfloat_result = r;
1889 goto exit_result_ok_cfloat;
1890 }
1891
1892 {
1893 PyObject *operand1_object = operand1;
1894 PyObject *operand2_object = Nuitka_PyLong_FromLong(operand2);
1895
1896 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
1897 assert(r != Py_NotImplemented);
1898
1899 Py_DECREF(operand2_object);
1900
1901 obj_result = r;
1902 goto exit_result_object;
1903 }
1904
1905exit_result_ok_cfloat:
1906 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
1907 goto exit_result_ok;
1908
1909exit_result_object:
1910 if (unlikely(obj_result == NULL)) {
1911 goto exit_result_exception;
1912 }
1913 result = obj_result;
1914 goto exit_result_ok;
1915
1916exit_result_ok_const_float_0_0:
1917 Py_INCREF(const_float_0_0);
1918 result = const_float_0_0;
1919 goto exit_result_ok;
1920
1921exit_result_ok_const_float_minus_0_0:
1922 Py_INCREF(const_float_minus_0_0);
1923 result = const_float_minus_0_0;
1924 goto exit_result_ok;
1925
1926exit_result_ok:
1927 return result;
1928
1929exit_result_exception:
1930 return NULL;
1931}
1932
1933PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_INT_CLONG(PyObject *operand1, long operand2) {
1934 return _BINARY_OPERATION_TRUEDIV_OBJECT_INT_CLONG(operand1, operand2);
1935}
1936#endif
1937
1938#if PYTHON_VERSION < 0x300
1939/* Code referring to "CLONG" corresponds to C platform long value and "INT" to Python2 'int'. */
1940static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_CLONG_INT(long operand1, PyObject *operand2) {
1941
1942 CHECK_OBJECT(operand2);
1943 assert(PyInt_CheckExact(operand2));
1944
1945 PyObject *result;
1946
1947 // Not every code path will make use of all possible results.
1948#if defined(_MSC_VER)
1949#pragma warning(push)
1950#pragma warning(disable : 4101)
1951#endif
1952 NUITKA_MAY_BE_UNUSED bool cbool_result;
1953 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
1954 NUITKA_MAY_BE_UNUSED long clong_result;
1955 NUITKA_MAY_BE_UNUSED double cfloat_result;
1956#if defined(_MSC_VER)
1957#pragma warning(pop)
1958#endif
1959
1960 CHECK_OBJECT(operand2);
1961 assert(PyInt_CheckExact(operand2));
1962
1963 const long a = operand1;
1964 const long b = PyInt_AS_LONG(operand2);
1965
1966 if (unlikely(b == 0)) {
1967 PyThreadState *tstate = PyThreadState_GET();
1968
1969 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
1970 goto exit_result_exception;
1971 }
1972
1973 if (a == 0) {
1974 if (b < 0) {
1975 goto exit_result_ok_const_float_minus_0_0;
1976 } else {
1977 goto exit_result_ok_const_float_0_0;
1978 }
1979 }
1980
1981/* May need to resort to LONG code, which we currently do not
1982 * specialize yet. TODO: Once we do that, call it here instead.
1983 */
1984#if DBL_MANT_DIG < WIDTH_OF_ULONG
1985 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
1986 } else
1987#endif
1988 {
1989 double r = (double)a / (double)b;
1990
1991 cfloat_result = r;
1992 goto exit_result_ok_cfloat;
1993 }
1994
1995 {
1996 PyObject *operand1_object = Nuitka_PyLong_FromLong(operand1);
1997 PyObject *operand2_object = operand2;
1998
1999 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
2000 assert(r != Py_NotImplemented);
2001
2002 Py_DECREF(operand1_object);
2003
2004 obj_result = r;
2005 goto exit_result_object;
2006 }
2007
2008exit_result_ok_cfloat:
2009 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
2010 goto exit_result_ok;
2011
2012exit_result_object:
2013 if (unlikely(obj_result == NULL)) {
2014 goto exit_result_exception;
2015 }
2016 result = obj_result;
2017 goto exit_result_ok;
2018
2019exit_result_ok_const_float_0_0:
2020 Py_INCREF(const_float_0_0);
2021 result = const_float_0_0;
2022 goto exit_result_ok;
2023
2024exit_result_ok_const_float_minus_0_0:
2025 Py_INCREF(const_float_minus_0_0);
2026 result = const_float_minus_0_0;
2027 goto exit_result_ok;
2028
2029exit_result_ok:
2030 return result;
2031
2032exit_result_exception:
2033 return NULL;
2034}
2035
2036PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_CLONG_INT(long operand1, PyObject *operand2) {
2037 return _BINARY_OPERATION_TRUEDIV_OBJECT_CLONG_INT(operand1, operand2);
2038}
2039#endif
2040
2041/* Code referring to "FLOAT" corresponds to Python 'float' and "CFLOAT" to C platform float value. */
2042static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_CFLOAT(PyObject *operand1, double operand2) {
2043 CHECK_OBJECT(operand1);
2044 assert(PyFloat_CheckExact(operand1));
2045
2046 PyObject *result;
2047
2048#if defined(_MSC_VER)
2049#pragma warning(push)
2050#pragma warning(disable : 4101)
2051#endif
2052 // Not every code path will make use of all possible results.
2053 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
2054 NUITKA_MAY_BE_UNUSED long clong_result;
2055 NUITKA_MAY_BE_UNUSED double cfloat_result;
2056#if defined(_MSC_VER)
2057#pragma warning(pop)
2058#endif
2059
2060 CHECK_OBJECT(operand1);
2061 assert(PyFloat_CheckExact(operand1));
2062
2063 const double a = PyFloat_AS_DOUBLE(operand1);
2064 const double b = operand2;
2065
2066 if (unlikely(b == 0.0)) {
2067 PyThreadState *tstate = PyThreadState_GET();
2068
2069 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "float division by zero");
2070 goto exit_result_exception;
2071 }
2072
2073 {
2074 double r = a / b;
2075
2076 cfloat_result = r;
2077 goto exit_result_ok_cfloat;
2078 }
2079
2080exit_result_ok_cfloat:
2081 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
2082 goto exit_result_ok;
2083
2084exit_result_ok:
2085 return result;
2086
2087exit_result_exception:
2088 return NULL;
2089}
2090
2091PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_CFLOAT(PyObject *operand1, double operand2) {
2092 return _BINARY_OPERATION_TRUEDIV_OBJECT_FLOAT_CFLOAT(operand1, operand2);
2093}
2094
2095/* Code referring to "CFLOAT" corresponds to C platform float value and "FLOAT" to Python 'float'. */
2096static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_CFLOAT_FLOAT(double operand1, PyObject *operand2) {
2097
2098 CHECK_OBJECT(operand2);
2099 assert(PyFloat_CheckExact(operand2));
2100
2101 PyObject *result;
2102
2103#if defined(_MSC_VER)
2104#pragma warning(push)
2105#pragma warning(disable : 4101)
2106#endif
2107 // Not every code path will make use of all possible results.
2108 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
2109 NUITKA_MAY_BE_UNUSED long clong_result;
2110 NUITKA_MAY_BE_UNUSED double cfloat_result;
2111#if defined(_MSC_VER)
2112#pragma warning(pop)
2113#endif
2114
2115 CHECK_OBJECT(operand2);
2116 assert(PyFloat_CheckExact(operand2));
2117
2118 const double a = operand1;
2119 const double b = PyFloat_AS_DOUBLE(operand2);
2120
2121 if (unlikely(b == 0.0)) {
2122 PyThreadState *tstate = PyThreadState_GET();
2123
2124 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "float division by zero");
2125 goto exit_result_exception;
2126 }
2127
2128 {
2129 double r = a / b;
2130
2131 cfloat_result = r;
2132 goto exit_result_ok_cfloat;
2133 }
2134
2135exit_result_ok_cfloat:
2136 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
2137 goto exit_result_ok;
2138
2139exit_result_ok:
2140 return result;
2141
2142exit_result_exception:
2143 return NULL;
2144}
2145
2146PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_CFLOAT_FLOAT(double operand1, PyObject *operand2) {
2147 return _BINARY_OPERATION_TRUEDIV_OBJECT_CFLOAT_FLOAT(operand1, operand2);
2148}
2149
2150/* Code referring to "OBJECT" corresponds to any Python object and "OBJECT" to any Python object. */
2151static PyObject *_BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_OBJECT(PyObject *operand1, PyObject *operand2) {
2152 CHECK_OBJECT(operand1);
2153 CHECK_OBJECT(operand2);
2154
2155#if PYTHON_VERSION < 0x300
2156 if (PyInt_CheckExact(operand1) && PyInt_CheckExact(operand2)) {
2157 PyObject *result;
2158
2159 // Not every code path will make use of all possible results.
2160#if defined(_MSC_VER)
2161#pragma warning(push)
2162#pragma warning(disable : 4101)
2163#endif
2164 NUITKA_MAY_BE_UNUSED bool cbool_result;
2165 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
2166 NUITKA_MAY_BE_UNUSED long clong_result;
2167 NUITKA_MAY_BE_UNUSED double cfloat_result;
2168#if defined(_MSC_VER)
2169#pragma warning(pop)
2170#endif
2171
2172 CHECK_OBJECT(operand1);
2173 assert(PyInt_CheckExact(operand1));
2174 CHECK_OBJECT(operand2);
2175 assert(PyInt_CheckExact(operand2));
2176
2177 const long a = PyInt_AS_LONG(operand1);
2178 const long b = PyInt_AS_LONG(operand2);
2179
2180 if (unlikely(b == 0)) {
2181 PyThreadState *tstate = PyThreadState_GET();
2182
2183 SET_CURRENT_EXCEPTION_TYPE0_STR(tstate, PyExc_ZeroDivisionError, "division by zero");
2184 goto exit_result_exception;
2185 }
2186
2187 if (a == 0) {
2188 if (b < 0) {
2189 goto exit_result_ok_const_float_minus_0_0;
2190 } else {
2191 goto exit_result_ok_const_float_0_0;
2192 }
2193 }
2194
2195/* May need to resort to LONG code, which we currently do not
2196 * specialize yet. TODO: Once we do that, call it here instead.
2197 */
2198#if DBL_MANT_DIG < WIDTH_OF_ULONG
2199 if ((a >= 0 ? 0UL + a : 0UL - a) >> DBL_MANT_DIG || (b >= 0 ? 0UL + b : 0UL - b) >> DBL_MANT_DIG) {
2200 } else
2201#endif
2202 {
2203 double r = (double)a / (double)b;
2204
2205 cfloat_result = r;
2206 goto exit_result_ok_cfloat;
2207 }
2208
2209 {
2210 PyObject *operand1_object = operand1;
2211 PyObject *operand2_object = operand2;
2212
2213 PyObject *r = PyLong_Type.tp_as_number->nb_true_divide(operand1_object, operand2_object);
2214 assert(r != Py_NotImplemented);
2215
2216 obj_result = r;
2217 goto exit_result_object;
2218 }
2219
2220 exit_result_ok_cfloat:
2221 result = MAKE_FLOAT_FROM_DOUBLE(cfloat_result);
2222 goto exit_result_ok;
2223
2224 exit_result_object:
2225 if (unlikely(obj_result == NULL)) {
2226 goto exit_result_exception;
2227 }
2228 result = obj_result;
2229 goto exit_result_ok;
2230
2231 exit_result_ok_const_float_0_0:
2232 Py_INCREF(const_float_0_0);
2233 result = const_float_0_0;
2234 goto exit_result_ok;
2235
2236 exit_result_ok_const_float_minus_0_0:
2237 Py_INCREF(const_float_minus_0_0);
2238 result = const_float_minus_0_0;
2239 goto exit_result_ok;
2240
2241 exit_result_ok:
2242 return result;
2243
2244 exit_result_exception:
2245 return NULL;
2246 }
2247#endif
2248
2249 PyTypeObject *type1 = Py_TYPE(operand1);
2250 PyTypeObject *type2 = Py_TYPE(operand2);
2251
2252#if defined(_MSC_VER)
2253#pragma warning(push)
2254#pragma warning(disable : 4101)
2255#endif
2256 NUITKA_MAY_BE_UNUSED bool cbool_result;
2257 NUITKA_MAY_BE_UNUSED PyObject *obj_result;
2258#if defined(_MSC_VER)
2259#pragma warning(pop)
2260#endif
2261
2262 binaryfunc slot1 =
2263 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_true_divide : NULL;
2264 binaryfunc slot2 = NULL;
2265
2266 if (!(type1 == type2)) {
2267 // Different types, need to consider second value slot.
2268
2269 slot2 =
2270 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_true_divide : NULL;
2271
2272 if (slot1 == slot2) {
2273 slot2 = NULL;
2274 }
2275 }
2276
2277 if (slot1 != NULL) {
2278 if (slot2 != NULL) {
2279 if (Nuitka_Type_IsSubtype(type2, type1)) {
2280 PyObject *x = slot2(operand1, operand2);
2281
2282 if (x != Py_NotImplemented) {
2283 obj_result = x;
2284 goto exit_binary_result_object;
2285 }
2286
2287 Py_DECREF_IMMORTAL(x);
2288 slot2 = NULL;
2289 }
2290 }
2291
2292 PyObject *x = slot1(operand1, operand2);
2293
2294 if (x != Py_NotImplemented) {
2295 obj_result = x;
2296 goto exit_binary_result_object;
2297 }
2298
2299 Py_DECREF_IMMORTAL(x);
2300 }
2301
2302 if (slot2 != NULL) {
2303 PyObject *x = slot2(operand1, operand2);
2304
2305 if (x != Py_NotImplemented) {
2306 obj_result = x;
2307 goto exit_binary_result_object;
2308 }
2309
2310 Py_DECREF_IMMORTAL(x);
2311 }
2312
2313#if PYTHON_VERSION < 0x300
2314 if (!NEW_STYLE_NUMBER_TYPE(type1) || !NEW_STYLE_NUMBER_TYPE(type2)) {
2315 coercion c1 =
2316 (type1->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type1)) ? type1->tp_as_number->nb_coerce : NULL;
2317
2318 if (c1 != NULL) {
2319 PyObject *coerced1 = operand1;
2320 PyObject *coerced2 = operand2;
2321
2322 int err = c1(&coerced1, &coerced2);
2323
2324 if (unlikely(err < 0)) {
2325 goto exit_binary_exception;
2326 }
2327
2328 if (err == 0) {
2329 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
2330
2331 if (likely(mv == NULL)) {
2332 binaryfunc slot = mv->nb_true_divide;
2333
2334 if (likely(slot != NULL)) {
2335 PyObject *x = slot(coerced1, coerced2);
2336
2337 Py_DECREF(coerced1);
2338 Py_DECREF(coerced2);
2339
2340 obj_result = x;
2341 goto exit_binary_result_object;
2342 }
2343 }
2344
2345 // nb_coerce took a reference.
2346 Py_DECREF(coerced1);
2347 Py_DECREF(coerced2);
2348 }
2349 }
2350 coercion c2 =
2351 (type2->tp_as_number != NULL && NEW_STYLE_NUMBER_TYPE(type2)) ? type2->tp_as_number->nb_coerce : NULL;
2352
2353 if (c2 != NULL) {
2354 PyObject *coerced1 = operand1;
2355 PyObject *coerced2 = operand2;
2356
2357 int err = c2(&coerced2, &coerced1);
2358
2359 if (unlikely(err < 0)) {
2360 goto exit_binary_exception;
2361 }
2362
2363 if (err == 0) {
2364 PyNumberMethods *mv = Py_TYPE(coerced1)->tp_as_number;
2365
2366 if (likely(mv == NULL)) {
2367 binaryfunc slot = mv->nb_true_divide;
2368
2369 if (likely(slot != NULL)) {
2370 PyObject *x = slot(coerced1, coerced2);
2371
2372 Py_DECREF(coerced1);
2373 Py_DECREF(coerced2);
2374
2375 obj_result = x;
2376 goto exit_binary_result_object;
2377 }
2378 }
2379
2380 // nb_coerce took a reference.
2381 Py_DECREF(coerced1);
2382 Py_DECREF(coerced2);
2383 }
2384 }
2385 }
2386#endif
2387
2388 PyErr_Format(PyExc_TypeError, "unsupported operand type(s) for /: '%s' and '%s'", type1->tp_name, type2->tp_name);
2389 goto exit_binary_exception;
2390
2391exit_binary_result_object:
2392 return obj_result;
2393
2394exit_binary_exception:
2395 return NULL;
2396}
2397
2398PyObject *BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_OBJECT(PyObject *operand1, PyObject *operand2) {
2399 return _BINARY_OPERATION_TRUEDIV_OBJECT_OBJECT_OBJECT(operand1, operand2);
2400}
2401
2402// Part of "Nuitka", an optimizing Python compiler that is compatible and
2403// integrates with CPython, but also works on its own.
2404//
2405// Licensed under the Apache License, Version 2.0 (the "License");
2406// you may not use this file except in compliance with the License.
2407// You may obtain a copy of the License at
2408//
2409// http://www.apache.org/licenses/LICENSE-2.0
2410//
2411// Unless required by applicable law or agreed to in writing, software
2412// distributed under the License is distributed on an "AS IS" BASIS,
2413// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
2414// See the License for the specific language governing permissions and
2415// limitations under the License.