Commit b3936524 authored by Stefan Behnel's avatar Stefan Behnel

clarify that C name specifications are not for everyday use

parent 259d392a
...@@ -213,52 +213,78 @@ Cython, with the same syntax as used by C compilers on Windows, for example,:: ...@@ -213,52 +213,78 @@ Cython, with the same syntax as used by C compilers on Windows, for example,::
If ``__stdcall`` is used, the function is only considered compatible with If ``__stdcall`` is used, the function is only considered compatible with
other ``__stdcall`` functions of the same signature. other ``__stdcall`` functions of the same signature.
Resolving naming conflicts - C name specifications Resolving naming conflicts - C name specifications
---------------------------------------------------- --------------------------------------------------
Each Cython module has a single module-level namespace for both Python and C Each Cython module has a single module-level namespace for both Python and C
names. This can be inconvenient if you want to wrap some external C functions names. This can be inconvenient if you want to wrap some external C functions
and provide the Python user with Python functions of the same names. and provide the Python user with Python functions of the same names.
Cython provides a couple of different ways of solving this problem. The Cython provides a couple of different ways of solving this problem. The best
best way, especially if you have many C functions to wrap, is probably to put way, especially if you have many C functions to wrap, is to put the extern
the extern C function declarations into a different namespace using the C function declarations into a ``.pxd`` file and thus a different namespace,
facilities described in the section on sharing declarations between Cython using the facilities described in the section on sharing declarations between
modules. Cython modules. Writing them into a ``.pxd`` file allows their reuse across
modules, avoids naming collisions in the normal Python way and even makes it
easy to rename them on cimport. For example, if your ``decl.pxd`` file
declared a C function ``eject_tomato``::
The other way is to use a C name specification to give different Cython and C cdef extern from "myheader.h":
names to the C function. Suppose, for example, that you want to wrap an void eject_tomato(float speed)
external function called :func:`eject_tomato`. If you declare it as::
cdef extern void c_eject_tomato "eject_tomato" (float speed) then you can cimport and wrap it in a ``.pyx`` file as follows::
then its name inside the Cython module will be ``c_eject_tomato``, whereas its name from decl cimport eject_tomato as c_eject_tomato
in C will be ``eject_tomato``. You can then wrap it with::
def eject_tomato(speed): def eject_tomato(speed):
c_eject_tomato(speed) c_eject_tomato(speed)
so that users of your module can refer to it as ``eject_tomato``. or simply cimport the ``.pxd`` file and use it as prefix::
cimport decl
def eject_tomato(speed):
decl.eject_tomato(speed)
For special cases where namespacing or renaming on import is not enough,
e.g. when a name in C conflicts with a Python keyword, you can use a C name
specification to give different Cython and C names to the C function at
declaration time. Suppose, for example, that you want to wrap an external
C function called :func:`yield`. If you declare it as::
cdef extern from "myheader.h":
void c_yield "yield" (float speed)
then its Cython visible name will be ``c_yield``, whereas its name in C
will be ``yield``. You can then wrap it with::
Another use for this feature is referring to external names that happen to be def call_yield(speed):
Cython keywords. For example, if you want to call an external function called c_yield(speed)
print, you can rename it to something else in your Cython module.
As well as functions, C names can be specified for variables, structs, unions, As for functions, C names can be specified for variables, structs, unions,
enums, struct and union members, and enum values. For example,:: enums, struct and union members, and enum values. For example::
cdef extern int one "ein", two "zwei" cdef extern int one "ein", two "zwei"
cdef extern float three "drei" cdef extern float three "drei"
cdef struct spam "SPAM": cdef struct spam "SPAM":
int i "eye" int i "eye"
cdef enum surprise "inquisition": cdef enum surprise "inquisition":
first "alpha" first "alpha"
second "beta" = 3 second "beta" = 3
Note that Cython will not do any validation or name mangling on the string
you provide. It will inject the bare text into the C code unmodified, so you
are entirely on your own with this feature. If you want to declare a name
``xyz`` and have Cython inject the text "make the C compiler fail here" into
the C file for it, you can do this using a C name declaration. Consider this
an advanced feature, only for the rare cases where everything else fails.
Using Cython Declarations from C Using Cython Declarations from C
================================== ================================
Cython provides two methods for making C declarations from a Cython module Cython provides two methods for making C declarations from a Cython module
available for use by external C code---public declarations and C API available for use by external C code---public declarations and C API
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment