File: bridge.py

package info (click to toggle)
pypy3 7.3.19%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 212,236 kB
  • sloc: python: 2,098,316; ansic: 540,565; sh: 21,462; asm: 14,419; cpp: 4,451; makefile: 4,209; objc: 761; xml: 530; exp: 499; javascript: 314; pascal: 244; lisp: 45; csh: 12; awk: 4
file content (44 lines) | stat: -rw-r--r-- 1,861 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
from rpython.rtyper.lltypesystem import lltype, rffi
from pypy.module._hpy_universal import llapi
from pypy.module._hpy_universal.apiset import APISet

# =============== HPy-RPython BRIDGE ===============
#
# Semi-complicate (but hopefully not too magic!) machinery to make it possible
# to call RPython functions from C in a way which works both before and after
# translation:
#
#   - during tests, the code runs on top of CPython, so we need ll2ctypes
#     callbacks: in bridge.h, a set of macros turn e.g. a call to foo() into
#     hpy_get_bridge()->foo()
#
#   - after translations, we want a direct call to the generated C functions

# NOTE: for bridge functions which take arguments of type "HPy", one more hack
# is needed. See the comment in bridge.h

# Adding a new bridge function is annoying because it involves modifying few
# different places: in theory it could be automated, but as long as the number
# of bridge function remains manageable, it is better to avoid adding
# unnecessary magic.  To add a new bridge function you need:
#
#   1. add the @BRIDGE.func decorator to your RPython function
#   2. add the corresponding field in _HPyBridge here
#   3. inside src/bridge.h:
#      a) add the corresponding field in _HPyBridge
#      b) write a macro for the RPYTHON_LL2CTYPES case
#      c) write the function prototype for the non-RPYTHON_LL2CTYPES case
#      d) if the func recevies HPy arguments, write a macro to convert them

llapi.cts.parse_source("""
typedef struct {
    void * hpy_err_Occurred_rpy;
    void * hpy_err_Clear;
} _HPyBridge;
""")

_HPyBridge = llapi.cts.gettype('_HPyBridge')
hpy_get_bridge = rffi.llexternal('hpy_get_bridge', [], lltype.Ptr(_HPyBridge),
                                 compilation_info=llapi.eci, _nowrapper=True)

BRIDGE = APISet(llapi.cts, mode="universal", prefix='^hpy_', force_c_name=True)