ยปCore Development>Code coverage>Modules/_ctypes/libffi/src/m68k/ffi.c

Python code coverage for Modules/_ctypes/libffi/src/m68k/ffi.c

#countcontent
1n/a/* -----------------------------------------------------------------------
2n/a ffi.c
3n/a
4n/a m68k Foreign Function Interface
5n/a ----------------------------------------------------------------------- */
6n/a
7n/a#include <ffi.h>
8n/a#include <ffi_common.h>
9n/a
10n/a#include <stdlib.h>
11n/a#include <unistd.h>
12n/a#ifdef __rtems__
13n/avoid rtems_cache_flush_multiple_data_lines( const void *, size_t );
14n/a#else
15n/a#include <sys/syscall.h>
16n/a#ifdef __MINT__
17n/a#include <mint/mintbind.h>
18n/a#include <mint/ssystem.h>
19n/a#else
20n/a#include <asm/cachectl.h>
21n/a#endif
22n/a#endif
23n/a
24n/avoid ffi_call_SYSV (extended_cif *,
25n/a unsigned, unsigned,
26n/a void *, void (*fn) ());
27n/avoid *ffi_prep_args (void *stack, extended_cif *ecif);
28n/avoid ffi_closure_SYSV (ffi_closure *);
29n/avoid ffi_closure_struct_SYSV (ffi_closure *);
30n/aunsigned int ffi_closure_SYSV_inner (ffi_closure *closure,
31n/a void *resp, void *args);
32n/a
33n/a/* ffi_prep_args is called by the assembly routine once stack space has
34n/a been allocated for the function's arguments. */
35n/a
36n/avoid *
37n/affi_prep_args (void *stack, extended_cif *ecif)
38n/a{
39n/a unsigned int i;
40n/a void **p_argv;
41n/a char *argp;
42n/a ffi_type **p_arg;
43n/a void *struct_value_ptr;
44n/a
45n/a argp = stack;
46n/a
47n/a if (
48n/a#ifdef __MINT__
49n/a (ecif->cif->rtype->type == FFI_TYPE_LONGDOUBLE) ||
50n/a#endif
51n/a (((ecif->cif->rtype->type == FFI_TYPE_STRUCT)
52n/a && !ecif->cif->flags)))
53n/a struct_value_ptr = ecif->rvalue;
54n/a else
55n/a struct_value_ptr = NULL;
56n/a
57n/a p_argv = ecif->avalue;
58n/a
59n/a for (i = ecif->cif->nargs, p_arg = ecif->cif->arg_types;
60n/a i != 0;
61n/a i--, p_arg++)
62n/a {
63n/a size_t z = (*p_arg)->size;
64n/a int type = (*p_arg)->type;
65n/a
66n/a if (z < sizeof (int))
67n/a {
68n/a switch (type)
69n/a {
70n/a case FFI_TYPE_SINT8:
71n/a *(signed int *) argp = (signed int) *(SINT8 *) *p_argv;
72n/a break;
73n/a
74n/a case FFI_TYPE_UINT8:
75n/a *(unsigned int *) argp = (unsigned int) *(UINT8 *) *p_argv;
76n/a break;
77n/a
78n/a case FFI_TYPE_SINT16:
79n/a *(signed int *) argp = (signed int) *(SINT16 *) *p_argv;
80n/a break;
81n/a
82n/a case FFI_TYPE_UINT16:
83n/a *(unsigned int *) argp = (unsigned int) *(UINT16 *) *p_argv;
84n/a break;
85n/a
86n/a case FFI_TYPE_STRUCT:
87n/a#ifdef __MINT__
88n/a if (z == 1 || z == 2)
89n/a memcpy (argp + 2, *p_argv, z);
90n/a else
91n/a memcpy (argp, *p_argv, z);
92n/a#else
93n/a memcpy (argp + sizeof (int) - z, *p_argv, z);
94n/a#endif
95n/a break;
96n/a
97n/a default:
98n/a FFI_ASSERT (0);
99n/a }
100n/a z = sizeof (int);
101n/a }
102n/a else
103n/a {
104n/a memcpy (argp, *p_argv, z);
105n/a
106n/a /* Align if necessary. */
107n/a if ((sizeof(int) - 1) & z)
108n/a z = ALIGN(z, sizeof(int));
109n/a }
110n/a
111n/a p_argv++;
112n/a argp += z;
113n/a }
114n/a
115n/a return struct_value_ptr;
116n/a}
117n/a
118n/a#define CIF_FLAGS_INT 1
119n/a#define CIF_FLAGS_DINT 2
120n/a#define CIF_FLAGS_FLOAT 4
121n/a#define CIF_FLAGS_DOUBLE 8
122n/a#define CIF_FLAGS_LDOUBLE 16
123n/a#define CIF_FLAGS_POINTER 32
124n/a#define CIF_FLAGS_STRUCT1 64
125n/a#define CIF_FLAGS_STRUCT2 128
126n/a#define CIF_FLAGS_SINT8 256
127n/a#define CIF_FLAGS_SINT16 512
128n/a
129n/a/* Perform machine dependent cif processing */
130n/affi_status
131n/affi_prep_cif_machdep (ffi_cif *cif)
132n/a{
133n/a /* Set the return type flag */
134n/a switch (cif->rtype->type)
135n/a {
136n/a case FFI_TYPE_VOID:
137n/a cif->flags = 0;
138n/a break;
139n/a
140n/a case FFI_TYPE_STRUCT:
141n/a if (cif->rtype->elements[0]->type == FFI_TYPE_STRUCT &&
142n/a cif->rtype->elements[1])
143n/a {
144n/a cif->flags = 0;
145n/a break;
146n/a }
147n/a
148n/a switch (cif->rtype->size)
149n/a {
150n/a case 1:
151n/a#ifdef __MINT__
152n/a cif->flags = CIF_FLAGS_STRUCT2;
153n/a#else
154n/a cif->flags = CIF_FLAGS_STRUCT1;
155n/a#endif
156n/a break;
157n/a case 2:
158n/a cif->flags = CIF_FLAGS_STRUCT2;
159n/a break;
160n/a#ifdef __MINT__
161n/a case 3:
162n/a#endif
163n/a case 4:
164n/a cif->flags = CIF_FLAGS_INT;
165n/a break;
166n/a#ifdef __MINT__
167n/a case 7:
168n/a#endif
169n/a case 8:
170n/a cif->flags = CIF_FLAGS_DINT;
171n/a break;
172n/a default:
173n/a cif->flags = 0;
174n/a break;
175n/a }
176n/a break;
177n/a
178n/a case FFI_TYPE_FLOAT:
179n/a cif->flags = CIF_FLAGS_FLOAT;
180n/a break;
181n/a
182n/a case FFI_TYPE_DOUBLE:
183n/a cif->flags = CIF_FLAGS_DOUBLE;
184n/a break;
185n/a
186n/a#if (FFI_TYPE_LONGDOUBLE != FFI_TYPE_DOUBLE)
187n/a case FFI_TYPE_LONGDOUBLE:
188n/a#ifdef __MINT__
189n/a cif->flags = 0;
190n/a#else
191n/a cif->flags = CIF_FLAGS_LDOUBLE;
192n/a#endif
193n/a break;
194n/a#endif
195n/a
196n/a case FFI_TYPE_POINTER:
197n/a cif->flags = CIF_FLAGS_POINTER;
198n/a break;
199n/a
200n/a case FFI_TYPE_SINT64:
201n/a case FFI_TYPE_UINT64:
202n/a cif->flags = CIF_FLAGS_DINT;
203n/a break;
204n/a
205n/a case FFI_TYPE_SINT16:
206n/a cif->flags = CIF_FLAGS_SINT16;
207n/a break;
208n/a
209n/a case FFI_TYPE_SINT8:
210n/a cif->flags = CIF_FLAGS_SINT8;
211n/a break;
212n/a
213n/a default:
214n/a cif->flags = CIF_FLAGS_INT;
215n/a break;
216n/a }
217n/a
218n/a return FFI_OK;
219n/a}
220n/a
221n/avoid
222n/affi_call (ffi_cif *cif, void (*fn) (), void *rvalue, void **avalue)
223n/a{
224n/a extended_cif ecif;
225n/a
226n/a ecif.cif = cif;
227n/a ecif.avalue = avalue;
228n/a
229n/a /* If the return value is a struct and we don't have a return value
230n/a address then we need to make one. */
231n/a
232n/a if (rvalue == NULL
233n/a && cif->rtype->type == FFI_TYPE_STRUCT
234n/a && cif->rtype->size > 8)
235n/a ecif.rvalue = alloca (cif->rtype->size);
236n/a else
237n/a ecif.rvalue = rvalue;
238n/a
239n/a switch (cif->abi)
240n/a {
241n/a case FFI_SYSV:
242n/a ffi_call_SYSV (&ecif, cif->bytes, cif->flags,
243n/a ecif.rvalue, fn);
244n/a break;
245n/a
246n/a default:
247n/a FFI_ASSERT (0);
248n/a break;
249n/a }
250n/a}
251n/a
252n/astatic void
253n/affi_prep_incoming_args_SYSV (char *stack, void **avalue, ffi_cif *cif)
254n/a{
255n/a unsigned int i;
256n/a void **p_argv;
257n/a char *argp;
258n/a ffi_type **p_arg;
259n/a
260n/a argp = stack;
261n/a p_argv = avalue;
262n/a
263n/a for (i = cif->nargs, p_arg = cif->arg_types; (i != 0); i--, p_arg++)
264n/a {
265n/a size_t z;
266n/a
267n/a z = (*p_arg)->size;
268n/a#ifdef __MINT__
269n/a if (cif->flags &&
270n/a cif->rtype->type == FFI_TYPE_STRUCT &&
271n/a (z == 1 || z == 2))
272n/a {
273n/a *p_argv = (void *) (argp + 2);
274n/a
275n/a z = 4;
276n/a }
277n/a else
278n/a if (cif->flags &&
279n/a cif->rtype->type == FFI_TYPE_STRUCT &&
280n/a (z == 3 || z == 4))
281n/a {
282n/a *p_argv = (void *) (argp);
283n/a
284n/a z = 4;
285n/a }
286n/a else
287n/a#endif
288n/a if (z <= 4)
289n/a {
290n/a *p_argv = (void *) (argp + 4 - z);
291n/a
292n/a z = 4;
293n/a }
294n/a else
295n/a {
296n/a *p_argv = (void *) argp;
297n/a
298n/a /* Align if necessary */
299n/a if ((sizeof(int) - 1) & z)
300n/a z = ALIGN(z, sizeof(int));
301n/a }
302n/a
303n/a p_argv++;
304n/a argp += z;
305n/a }
306n/a}
307n/a
308n/aunsigned int
309n/affi_closure_SYSV_inner (ffi_closure *closure, void *resp, void *args)
310n/a{
311n/a ffi_cif *cif;
312n/a void **arg_area;
313n/a
314n/a cif = closure->cif;
315n/a arg_area = (void**) alloca (cif->nargs * sizeof (void *));
316n/a
317n/a ffi_prep_incoming_args_SYSV(args, arg_area, cif);
318n/a
319n/a (closure->fun) (cif, resp, arg_area, closure->user_data);
320n/a
321n/a return cif->flags;
322n/a}
323n/a
324n/affi_status
325n/affi_prep_closure_loc (ffi_closure* closure,
326n/a ffi_cif* cif,
327n/a void (*fun)(ffi_cif*,void*,void**,void*),
328n/a void *user_data,
329n/a void *codeloc)
330n/a{
331n/a if (cif->abi != FFI_SYSV)
332n/a return FFI_BAD_ABI;
333n/a
334n/a *(unsigned short *)closure->tramp = 0x207c;
335n/a *(void **)(closure->tramp + 2) = codeloc;
336n/a *(unsigned short *)(closure->tramp + 6) = 0x4ef9;
337n/a
338n/a if (
339n/a#ifdef __MINT__
340n/a (cif->rtype->type == FFI_TYPE_LONGDOUBLE) ||
341n/a#endif
342n/a (((cif->rtype->type == FFI_TYPE_STRUCT)
343n/a && !cif->flags)))
344n/a *(void **)(closure->tramp + 8) = ffi_closure_struct_SYSV;
345n/a else
346n/a *(void **)(closure->tramp + 8) = ffi_closure_SYSV;
347n/a
348n/a#ifdef __rtems__
349n/a rtems_cache_flush_multiple_data_lines( codeloc, FFI_TRAMPOLINE_SIZE );
350n/a#elif defined(__MINT__)
351n/a Ssystem(S_FLUSHCACHE, codeloc, FFI_TRAMPOLINE_SIZE);
352n/a#else
353n/a syscall(SYS_cacheflush, codeloc, FLUSH_SCOPE_LINE,
354n/a FLUSH_CACHE_BOTH, FFI_TRAMPOLINE_SIZE);
355n/a#endif
356n/a
357n/a closure->cif = cif;
358n/a closure->user_data = user_data;
359n/a closure->fun = fun;
360n/a
361n/a return FFI_OK;
362n/a}