blob: 9b6440e1c2ab1cb26b7295582e5eec5607d19f26 [file] [log] [blame]
Stefan Krah39042e02020-08-10 16:32:21 +02001/*
2 * Copyright (c) 2020 Stefan Krah. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 *
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS "AS IS" AND
16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 * SUCH DAMAGE.
26 */
27
28
29#ifndef CPYTHON_DECIMAL_H_
30#define CPYTHON_DECIMAL_H_
31
32
33#include <Python.h>
34
35#ifdef __cplusplus
36extern "C" {
37#endif
38
39/****************************************************************************/
40/* Libmpdec API */
41/****************************************************************************/
42
43#ifndef LIBMPDEC_MPDECIMAL_H_
44struct mpd_t; /* ABI-stable in the libmpdec-2.x series */
45
46/* status cases for getting a triple */
47enum mpd_triple_class {
48 MPD_TRIPLE_NORMAL,
49 MPD_TRIPLE_INF,
50 MPD_TRIPLE_QNAN,
51 MPD_TRIPLE_SNAN,
52 MPD_TRIPLE_ERROR,
53};
54
55typedef struct {
56 enum mpd_triple_class tag;
57 uint8_t sign;
58 uint64_t hi;
59 uint64_t lo;
60 int64_t exp;
61} mpd_uint128_triple_t;
62#endif
63
64
65/****************************************************************************/
66/* Capsule API */
67/****************************************************************************/
68
69/* Simple API */
70#define PyDec_TypeCheck_INDEX 0
71#define PyDec_TypeCheck_RETURN int
72#define PyDec_TypeCheck_ARGS (const PyObject *)
73
74#define PyDec_IsSpecial_INDEX 1
75#define PyDec_IsSpecial_RETURN int
76#define PyDec_IsSpecial_ARGS (const PyObject *)
77
78#define PyDec_IsNaN_INDEX 2
79#define PyDec_IsNaN_RETURN int
80#define PyDec_IsNaN_ARGS (const PyObject *)
81
82#define PyDec_IsInfinite_INDEX 3
83#define PyDec_IsInfinite_RETURN int
84#define PyDec_IsInfinite_ARGS (const PyObject *)
85
86#define PyDec_GetDigits_INDEX 4
87#define PyDec_GetDigits_RETURN int64_t
88#define PyDec_GetDigits_ARGS (const PyObject *)
89
90#define PyDec_AsUint128Triple_INDEX 5
91#define PyDec_AsUint128Triple_RETURN mpd_uint128_triple_t
92#define PyDec_AsUint128Triple_ARGS (const PyObject *)
93
94#define PyDec_FromUint128Triple_INDEX 6
95#define PyDec_FromUint128Triple_RETURN PyObject *
96#define PyDec_FromUint128Triple_ARGS (const mpd_uint128_triple_t *triple)
97
98/* Advanced API */
99#define PyDec_Alloc_INDEX 7
100#define PyDec_Alloc_RETURN PyObject *
101#define PyDec_Alloc_ARGS (void)
102
103#define PyDec_Get_INDEX 8
104#define PyDec_Get_RETURN mpd_t *
105#define PyDec_Get_ARGS (PyObject *)
106
107#define PyDec_GetConst_INDEX 9
108#define PyDec_GetConst_RETURN const mpd_t *
109#define PyDec_GetConst_ARGS (const PyObject *)
110
111#define CPYTHON_DECIMAL_MAX_API 10
112
113
114#ifdef CPYTHON_DECIMAL_MODULE
115/* Simple API */
116static PyDec_TypeCheck_RETURN PyDec_TypeCheck PyDec_TypeCheck_ARGS;
117static PyDec_IsSpecial_RETURN PyDec_IsSpecial PyDec_IsSpecial_ARGS;
118static PyDec_IsNaN_RETURN PyDec_IsNaN PyDec_IsNaN_ARGS;
119static PyDec_IsInfinite_RETURN PyDec_IsInfinite PyDec_IsInfinite_ARGS;
120static PyDec_GetDigits_RETURN PyDec_GetDigits PyDec_GetDigits_ARGS;
121static PyDec_AsUint128Triple_RETURN PyDec_AsUint128Triple PyDec_AsUint128Triple_ARGS;
122static PyDec_FromUint128Triple_RETURN PyDec_FromUint128Triple PyDec_FromUint128Triple_ARGS;
123
124/* Advanced API */
125static PyDec_Alloc_RETURN PyDec_Alloc PyDec_Alloc_ARGS;
126static PyDec_Get_RETURN PyDec_Get PyDec_Get_ARGS;
127static PyDec_GetConst_RETURN PyDec_GetConst PyDec_GetConst_ARGS;
128#else
129static void **_decimal_api;
130
131/* Simple API */
132#define PyDec_TypeCheck \
133 (*(PyDec_TypeCheck_RETURN (*)PyDec_TypeCheck_ARGS) _decimal_api[PyDec_TypeCheck_INDEX])
134
135#define PyDec_IsSpecial \
136 (*(PyDec_IsSpecial_RETURN (*)PyDec_IsSpecial_ARGS) _decimal_api[PyDec_IsSpecial_INDEX])
137
138#define PyDec_IsNaN \
139 (*(PyDec_IsNaN_RETURN (*)PyDec_IsNaN_ARGS) _decimal_api[PyDec_IsNaN_INDEX])
140
141#define PyDec_IsInfinite \
142 (*(PyDec_IsInfinite_RETURN (*)PyDec_IsInfinite_ARGS) _decimal_api[PyDec_IsInfinite_INDEX])
143
144#define PyDec_GetDigits \
145 (*(PyDec_GetDigits_RETURN (*)PyDec_GetDigits_ARGS) _decimal_api[PyDec_GetDigits_INDEX])
146
147#define PyDec_AsUint128Triple \
148 (*(PyDec_AsUint128Triple_RETURN (*)PyDec_AsUint128Triple_ARGS) _decimal_api[PyDec_AsUint128Triple_INDEX])
149
150#define PyDec_FromUint128Triple \
151 (*(PyDec_FromUint128Triple_RETURN (*)PyDec_FromUint128Triple_ARGS) _decimal_api[PyDec_FromUint128Triple_INDEX])
152
153/* Advanced API */
154#define PyDec_Alloc \
155 (*(PyDec_Alloc_RETURN (*)PyDec_Alloc_ARGS) _decimal_api[PyDec_Alloc_INDEX])
156
157#define PyDec_Get \
158 (*(PyDec_Get_RETURN (*)PyDec_Get_ARGS) _decimal_api[PyDec_Get_INDEX])
159
160#define PyDec_GetConst \
161 (*(PyDec_GetConst_RETURN (*)PyDec_GetConst_ARGS) _decimal_api[PyDec_GetConst_INDEX])
162
163
164static int
165import_decimal(void)
166{
167 _decimal_api = (void **)PyCapsule_Import("_decimal._API", 0);
168 if (_decimal_api == NULL) {
169 return -1;
170 }
171
172 return 0;
173}
174#endif
175
176#ifdef __cplusplus
177}
178#endif
179
180#endif /* CPYTHON_DECIMAL_H_ */