Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
cython
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Labels
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Commits
Open sidebar
nexedi
cython
Commits
0a56c99d
Commit
0a56c99d
authored
Mar 31, 2011
by
Lisandro Dalcin
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
public/capi: fixes and cleanups, implement exporting cdef variables
parent
b5037005
Changes
12
Show whitespace changes
Inline
Side-by-side
Showing
12 changed files
with
613 additions
and
152 deletions
+613
-152
Cython/Compiler/ModuleNode.py
Cython/Compiler/ModuleNode.py
+209
-78
Cython/Compiler/Nodes.py
Cython/Compiler/Nodes.py
+23
-24
Cython/Compiler/Parsing.py
Cython/Compiler/Parsing.py
+11
-7
Cython/Compiler/PyrexTypes.py
Cython/Compiler/PyrexTypes.py
+2
-2
Cython/Compiler/Symtab.py
Cython/Compiler/Symtab.py
+50
-40
tests/compile/a_capi.pyx
tests/compile/a_capi.pyx
+6
-0
tests/compile/publicapi_api.pyx
tests/compile/publicapi_api.pyx
+65
-0
tests/compile/publicapi_mix.pyx
tests/compile/publicapi_mix.pyx
+77
-0
tests/compile/publicapi_pub.pyx
tests/compile/publicapi_pub.pyx
+65
-0
tests/compile/publicapi_pxd_mix.pxd
tests/compile/publicapi_pxd_mix.pxd
+68
-0
tests/compile/publicapi_pxd_mix.pyx
tests/compile/publicapi_pxd_mix.pyx
+15
-0
tests/run/capiimpl.pyx
tests/run/capiimpl.pyx
+22
-1
No files found.
Cython/Compiler/ModuleNode.py
View file @
0a56c99d
...
@@ -96,14 +96,16 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -96,14 +96,16 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
f
.
close
()
f
.
close
()
def
generate_h_code
(
self
,
env
,
options
,
result
):
def
generate_h_code
(
self
,
env
,
options
,
result
):
def
h_entries
(
entries
,
pxd
=
0
):
def
h_entries
(
entries
,
api
=
0
,
pxd
=
0
):
return
[
entry
for
entry
in
entries
return
[
entry
for
entry
in
entries
if
entry
.
visibility
==
'public'
or
pxd
and
entry
.
defined_in_pxd
]
if
((
entry
.
visibility
==
'public'
)
or
h_types
=
h_entries
(
env
.
type_entries
)
(
api
and
entry
.
api
)
or
(
pxd
and
entry
.
defined_in_pxd
))]
h_types
=
h_entries
(
env
.
type_entries
,
api
=
1
)
h_vars
=
h_entries
(
env
.
var_entries
)
h_vars
=
h_entries
(
env
.
var_entries
)
h_funcs
=
h_entries
(
env
.
cfunc_entries
)
h_funcs
=
h_entries
(
env
.
cfunc_entries
)
h_extension_types
=
h_entries
(
env
.
c_class_entries
)
h_extension_types
=
h_entries
(
env
.
c_class_entries
)
if
h_types
or
h_vars
or
h_funcs
or
h_extension_types
:
if
(
h_types
or
h_vars
or
h_funcs
or
h_extension_types
)
:
result
.
h_file
=
replace_suffix
(
result
.
c_file
,
".h"
)
result
.
h_file
=
replace_suffix
(
result
.
c_file
,
".h"
)
h_code
=
Code
.
CCodeWriter
()
h_code
=
Code
.
CCodeWriter
()
Code
.
GlobalState
(
h_code
)
Code
.
GlobalState
(
h_code
)
...
@@ -115,31 +117,37 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -115,31 +117,37 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
h_guard
=
Naming
.
h_guard_prefix
+
self
.
api_name
(
env
)
h_guard
=
Naming
.
h_guard_prefix
+
self
.
api_name
(
env
)
h_code
.
put_h_guard
(
h_guard
)
h_code
.
put_h_guard
(
h_guard
)
self
.
generate_extern_c_macro_definition
(
h_code
)
h_code
.
putln
(
""
)
self
.
generate_type_header_code
(
h_types
,
h_code
)
self
.
generate_type_header_code
(
h_types
,
h_code
)
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
api_guard
=
Naming
.
api_guard_prefix
+
self
.
api_name
(
env
)
api_guard
=
Naming
.
api_guard_prefix
+
self
.
api_name
(
env
)
h_code
.
putln
(
"#ifndef %s"
%
api_guard
)
h_code
.
putln
(
"#ifndef %s"
%
api_guard
)
if
h_vars
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
for
entry
in
h_vars
:
self
.
generate_extern_c_macro_definition
(
h_code
)
self
.
generate_public_declaration
(
entry
,
h_code
,
i_code
)
if
h_funcs
:
h_code
.
putln
(
""
)
for
entry
in
h_funcs
:
self
.
generate_public_declaration
(
entry
,
h_code
,
i_code
)
if
h_extension_types
:
if
h_extension_types
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
for
entry
in
h_extension_types
:
for
entry
in
h_extension_types
:
self
.
generate_cclass_header_code
(
entry
.
type
,
h_code
)
self
.
generate_cclass_header_code
(
entry
.
type
,
h_code
)
if
i_code
:
if
i_code
:
self
.
generate_cclass_include_code
(
entry
.
type
,
i_code
)
self
.
generate_cclass_include_code
(
entry
.
type
,
i_code
)
if
h_funcs
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"#endif"
)
for
entry
in
h_funcs
:
self
.
generate_public_declaration
(
entry
,
h_code
,
i_code
)
if
h_vars
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"PyMODINIT_FUNC init%s(void);"
%
env
.
module_name
)
for
entry
in
h_vars
:
self
.
generate_public_declaration
(
entry
,
h_code
,
i_code
)
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"#endif /* !%s */"
%
api_guard
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"#if PY_MAJOR_VERSION < 3"
)
h_code
.
putln
(
"PyMODINIT_FUNC init%s(void);"
%
env
.
module_name
)
h_code
.
putln
(
"#else"
)
h_code
.
putln
(
"PyMODINIT_FUNC PyInit_%s(void);"
%
env
.
module_name
)
h_code
.
putln
(
"#endif"
)
h_code
.
putln
(
"#endif"
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"#endif /* !%s */"
%
h_guard
)
f
=
open_new_file
(
result
.
h_file
)
f
=
open_new_file
(
result
.
h_file
)
try
:
try
:
...
@@ -160,63 +168,68 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -160,63 +168,68 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
return
env
.
qualified_name
.
replace
(
"."
,
"__"
)
return
env
.
qualified_name
.
replace
(
"."
,
"__"
)
def
generate_api_code
(
self
,
env
,
result
):
def
generate_api_code
(
self
,
env
,
result
):
api_funcs
=
[]
def
api_entries
(
entries
,
pxd
=
1
):
public_extension_types
=
[]
return
[
entry
for
entry
in
entries
has_api_extension_types
=
0
if
entry
.
api
or
(
pxd
and
entry
.
defined_in_pxd
)]
for
entry
in
env
.
cfunc_entries
:
api_vars
=
api_entries
(
env
.
var_entries
)
if
entry
.
api
:
api_funcs
=
api_entries
(
env
.
cfunc_entries
)
api_funcs
.
append
(
entry
)
api_extension_types
=
api_entries
(
env
.
c_class_entries
)
for
entry
in
env
.
c_class_entries
:
if
api_vars
or
api_funcs
or
api_extension_types
:
if
entry
.
visibility
==
'public'
:
public_extension_types
.
append
(
entry
)
if
entry
.
api
:
has_api_extension_types
=
1
if
api_funcs
or
has_api_extension_types
:
result
.
api_file
=
replace_suffix
(
result
.
c_file
,
"_api.h"
)
result
.
api_file
=
replace_suffix
(
result
.
c_file
,
"_api.h"
)
h_code
=
Code
.
CCodeWriter
()
h_code
=
Code
.
CCodeWriter
()
Code
.
GlobalState
(
h_code
)
Code
.
GlobalState
(
h_code
)
name
=
self
.
api_name
(
env
)
api_guard
=
Naming
.
api_guard_prefix
+
self
.
api_name
(
env
)
guard
=
Naming
.
api_guard_prefix
+
name
h_code
.
put_h_guard
(
api_guard
)
h_code
.
put_h_guard
(
guard
)
h_code
.
putln
(
'#include "Python.h"'
)
h_code
.
putln
(
'#include "Python.h"'
)
if
result
.
h_file
:
if
result
.
h_file
:
h_code
.
putln
(
'#include "%s"'
%
os
.
path
.
basename
(
result
.
h_file
))
h_code
.
putln
(
'#include "%s"'
%
os
.
path
.
basename
(
result
.
h_file
))
for
entry
in
public_extension_types
:
if
api_extension_types
:
type
=
entry
.
type
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"static PyTypeObject *%s;"
%
type
.
typeptr_cname
)
for
entry
in
api_extension_types
:
type
=
entry
.
type
h_code
.
putln
(
"static PyTypeObject *%s = 0;"
%
type
.
typeptr_cname
)
h_code
.
putln
(
"#define %s (*%s)"
%
(
h_code
.
putln
(
"#define %s (*%s)"
%
(
type
.
typeobj_cname
,
type
.
typeptr_cname
))
type
.
typeobj_cname
,
type
.
typeptr_cname
))
if
api_funcs
:
if
api_funcs
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
for
entry
in
api_funcs
:
for
entry
in
api_funcs
:
type
=
CPtrType
(
entry
.
type
)
type
=
CPtrType
(
entry
.
type
)
h_code
.
putln
(
"static %s;"
%
type
.
declaration_code
(
entry
.
cname
))
cname
=
env
.
mangle
(
Naming
.
func_prefix
,
entry
.
name
)
h_code
.
putln
(
"static %s = 0;"
%
type
.
declaration_code
(
cname
))
h_code
.
putln
(
"#define %s %s"
%
(
entry
.
name
,
cname
))
if
api_vars
:
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
put_h_guard
(
Naming
.
api_func_guard
+
"import_module"
)
for
entry
in
api_vars
:
type
=
CPtrType
(
entry
.
type
)
cname
=
env
.
mangle
(
Naming
.
var_prefix
,
entry
.
name
)
h_code
.
putln
(
"static %s = 0;"
%
type
.
declaration_code
(
cname
))
h_code
.
putln
(
"#define %s (*%s)"
%
(
entry
.
name
,
cname
))
h_code
.
put
(
import_module_utility_code
.
impl
)
h_code
.
put
(
import_module_utility_code
.
impl
)
h_code
.
putln
(
""
)
if
api_vars
:
h_code
.
putln
(
"#endif"
)
h_code
.
put
(
voidptr_import_utility_code
.
impl
)
if
api_funcs
:
if
api_funcs
:
h_code
.
putln
(
""
)
h_code
.
put
(
function_import_utility_code
.
impl
)
h_code
.
put
(
function_import_utility_code
.
impl
)
if
public_extension_types
:
if
api_extension_types
:
h_code
.
putln
(
""
)
h_code
.
put
(
type_import_utility_code
.
impl
)
h_code
.
put
(
type_import_utility_code
.
impl
)
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"static int import_%s(void) {"
%
name
)
h_code
.
putln
(
"static int import_%s(void) {"
%
self
.
api_name
(
env
)
)
h_code
.
putln
(
"PyObject *module = 0;"
)
h_code
.
putln
(
"PyObject *module = 0;"
)
h_code
.
putln
(
'module = __Pyx_ImportModule("%s");'
%
env
.
qualified_name
)
h_code
.
putln
(
'module = __Pyx_ImportModule("%s");'
%
env
.
qualified_name
)
h_code
.
putln
(
"if (!module) goto bad;"
)
h_code
.
putln
(
"if (!module) goto bad;"
)
for
entry
in
api_funcs
:
for
entry
in
api_funcs
:
cname
=
env
.
mangle
(
Naming
.
func_prefix
,
entry
.
name
)
sig
=
entry
.
type
.
signature_string
()
sig
=
entry
.
type
.
signature_string
()
h_code
.
putln
(
h_code
.
putln
(
'if (__Pyx_ImportFunction(module, "%s", (void (**)(void))&%s, "%s") < 0) goto bad;'
%
(
'if (__Pyx_ImportFunction(module, "%s", (void (**)(void))&%s, "%s") < 0) goto bad;'
entry
.
name
,
%
(
entry
.
name
,
cname
,
sig
))
entry
.
cname
,
for
entry
in
api_vars
:
sig
))
cname
=
env
.
mangle
(
Naming
.
var_prefix
,
entry
.
name
)
sig
=
entry
.
type
.
declaration_code
(
""
)
h_code
.
putln
(
'if (__Pyx_ImportVoidPtr(module, "%s", (void **)&%s, "%s") < 0) goto bad;'
%
(
entry
.
name
,
cname
,
sig
))
h_code
.
putln
(
"Py_DECREF(module); module = 0;"
)
h_code
.
putln
(
"Py_DECREF(module); module = 0;"
)
for
entry
in
public
_extension_types
:
for
entry
in
api
_extension_types
:
self
.
generate_type_import_call
(
self
.
generate_type_import_call
(
entry
.
type
,
h_code
,
entry
.
type
,
h_code
,
"if (!%s) goto bad;"
%
entry
.
type
.
typeptr_cname
)
"if (!%s) goto bad;"
%
entry
.
type
.
typeptr_cname
)
...
@@ -226,7 +239,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -226,7 +239,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
h_code
.
putln
(
"return -1;"
)
h_code
.
putln
(
"return -1;"
)
h_code
.
putln
(
"}"
)
h_code
.
putln
(
"}"
)
h_code
.
putln
(
""
)
h_code
.
putln
(
""
)
h_code
.
putln
(
"#endif
"
)
h_code
.
putln
(
"#endif
/* !%s */"
%
api_guard
)
f
=
open_new_file
(
result
.
api_file
)
f
=
open_new_file
(
result
.
api_file
)
try
:
try
:
...
@@ -235,8 +248,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -235,8 +248,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
f
.
close
()
f
.
close
()
def
generate_cclass_header_code
(
self
,
type
,
h_code
):
def
generate_cclass_header_code
(
self
,
type
,
h_code
):
h_code
.
putln
(
"%s
DL_IMPORT(PyTypeObject)
%s;"
%
(
h_code
.
putln
(
"%s
%s
%s;"
%
(
Naming
.
extern_c_macro
,
Naming
.
extern_c_macro
,
PyrexTypes
.
public_decl
(
"PyTypeObject"
,
"DL_IMPORT"
),
type
.
typeobj_cname
))
type
.
typeobj_cname
))
def
generate_cclass_include_code
(
self
,
type
,
i_code
):
def
generate_cclass_include_code
(
self
,
type
,
i_code
):
...
@@ -426,8 +440,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -426,8 +440,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
self
.
generate_objstruct_definition
(
type
,
code
)
self
.
generate_objstruct_definition
(
type
,
code
)
for
entry
in
vtabslot_list
:
for
entry
in
vtabslot_list
:
self
.
generate_objstruct_definition
(
entry
.
type
,
code
)
self
.
generate_objstruct_definition
(
entry
.
type
,
code
)
self
.
generate_typeobj_predeclaration
(
entry
,
code
)
for
entry
in
vtab_list
:
for
entry
in
vtab_list
:
self
.
generate_typeobj
ect
_predeclaration
(
entry
,
code
)
self
.
generate_typeobj_predeclaration
(
entry
,
code
)
self
.
generate_exttype_vtable_struct
(
entry
,
code
)
self
.
generate_exttype_vtable_struct
(
entry
,
code
)
self
.
generate_exttype_vtabptr_declaration
(
entry
,
code
)
self
.
generate_exttype_vtabptr_declaration
(
entry
,
code
)
...
@@ -724,10 +739,12 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -724,10 +739,12 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
def
generate_extern_c_macro_definition
(
self
,
code
):
def
generate_extern_c_macro_definition
(
self
,
code
):
name
=
Naming
.
extern_c_macro
name
=
Naming
.
extern_c_macro
code
.
putln
(
"#ifdef __cplusplus"
)
code
.
putln
(
"#ifndef %s"
%
name
)
code
.
putln
(
'#define %s extern "C"'
%
name
)
code
.
putln
(
" #ifdef __cplusplus"
)
code
.
putln
(
"#else"
)
code
.
putln
(
' #define %s extern "C"'
%
name
)
code
.
putln
(
"#define %s extern"
%
name
)
code
.
putln
(
" #else"
)
code
.
putln
(
" #define %s extern"
%
name
)
code
.
putln
(
" #endif"
)
code
.
putln
(
"#endif"
)
code
.
putln
(
"#endif"
)
def
generate_includes
(
self
,
env
,
cimported_modules
,
code
):
def
generate_includes
(
self
,
env
,
cimported_modules
,
code
):
...
@@ -789,10 +806,13 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -789,10 +806,13 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
def
generate_typedef
(
self
,
entry
,
code
):
def
generate_typedef
(
self
,
entry
,
code
):
base_type
=
entry
.
type
.
typedef_base_type
base_type
=
entry
.
type
.
typedef_base_type
if
base_type
.
is_numeric
:
if
base_type
.
is_numeric
:
try
:
writer
=
code
.
globalstate
[
'numeric_typedefs'
]
writer
=
code
.
globalstate
[
'numeric_typedefs'
]
except
KeyError
:
writer
=
code
else
:
else
:
writer
=
code
writer
=
code
writer
.
putln
(
""
)
writer
.
mark_pos
(
entry
.
pos
)
writer
.
putln
(
"typedef %s;"
%
base_type
.
declaration_code
(
entry
.
cname
))
writer
.
putln
(
"typedef %s;"
%
base_type
.
declaration_code
(
entry
.
cname
))
def
sue_header_footer
(
self
,
type
,
kind
,
name
):
def
sue_header_footer
(
self
,
type
,
kind
,
name
):
...
@@ -816,7 +836,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -816,7 +836,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
code
.
globalstate
.
use_utility_code
(
packed_struct_utility_code
)
code
.
globalstate
.
use_utility_code
(
packed_struct_utility_code
)
header
,
footer
=
\
header
,
footer
=
\
self
.
sue_header_footer
(
type
,
kind
,
type
.
cname
)
self
.
sue_header_footer
(
type
,
kind
,
type
.
cname
)
code
.
putln
(
""
)
if
packed
:
if
packed
:
code
.
putln
(
"#if defined(__SUNPRO_C)"
)
code
.
putln
(
"#if defined(__SUNPRO_C)"
)
code
.
putln
(
" #pragma pack(1)"
)
code
.
putln
(
" #pragma pack(1)"
)
...
@@ -847,7 +866,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -847,7 +866,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
name
=
entry
.
cname
or
entry
.
name
or
""
name
=
entry
.
cname
or
entry
.
name
or
""
header
,
footer
=
\
header
,
footer
=
\
self
.
sue_header_footer
(
type
,
"enum"
,
name
)
self
.
sue_header_footer
(
type
,
"enum"
,
name
)
code
.
putln
(
""
)
code
.
putln
(
header
)
code
.
putln
(
header
)
enum_values
=
entry
.
enum_values
enum_values
=
entry
.
enum_values
if
not
enum_values
:
if
not
enum_values
:
...
@@ -873,21 +891,23 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -873,21 +891,23 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
code
.
putln
(
value_code
)
code
.
putln
(
value_code
)
code
.
putln
(
footer
)
code
.
putln
(
footer
)
def
generate_typeobj
ect
_predeclaration
(
self
,
entry
,
code
):
def
generate_typeobj_predeclaration
(
self
,
entry
,
code
):
code
.
putln
(
""
)
code
.
putln
(
""
)
name
=
entry
.
type
.
typeobj_cname
name
=
entry
.
type
.
typeobj_cname
if
name
:
if
name
:
if
entry
.
visibility
==
'extern'
and
not
entry
.
in_cinclude
:
if
entry
.
visibility
==
'extern'
and
not
entry
.
in_cinclude
:
code
.
putln
(
"%s
DL_IMPORT(PyTypeObject)
%s;"
%
(
code
.
putln
(
"%s
%s
%s;"
%
(
Naming
.
extern_c_macro
,
Naming
.
extern_c_macro
,
PyrexTypes
.
public_decl
(
"PyTypeObject"
,
"DL_IMPORT"
),
name
))
name
))
elif
entry
.
visibility
==
'public'
:
elif
entry
.
visibility
==
'public'
:
code
.
putln
(
"%s
DL_EXPORT(PyTypeObject)
%s;"
%
(
code
.
putln
(
"%s
%s
%s;"
%
(
Naming
.
extern_c_macro
,
Naming
.
extern_c_macro
,
PyrexTypes
.
public_decl
(
"PyTypeObject"
,
"DL_EXPORT"
),
name
))
name
))
# ??? Do we really need the rest of this? ???
# ??? Do we really need the rest of this? ???
#else:
#else:
# code.putln("static
forward
PyTypeObject %s;" % name)
# code.putln("static PyTypeObject %s;" % name)
def
generate_exttype_vtable_struct
(
self
,
entry
,
code
):
def
generate_exttype_vtable_struct
(
self
,
entry
,
code
):
code
.
mark_pos
(
entry
.
pos
)
code
.
mark_pos
(
entry
.
pos
)
...
@@ -927,7 +947,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -927,7 +947,6 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
return
# Forward declared but never defined
return
# Forward declared but never defined
header
,
footer
=
\
header
,
footer
=
\
self
.
sue_header_footer
(
type
,
"struct"
,
type
.
objstruct_cname
)
self
.
sue_header_footer
(
type
,
"struct"
,
type
.
objstruct_cname
)
code
.
putln
(
""
)
code
.
putln
(
header
)
code
.
putln
(
header
)
base_type
=
type
.
base_type
base_type
=
type
.
base_type
if
base_type
:
if
base_type
:
...
@@ -966,24 +985,26 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -966,24 +985,26 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
for
entry
in
env
.
cfunc_entries
:
for
entry
in
env
.
cfunc_entries
:
if
entry
.
inline_func_in_pxd
or
(
not
entry
.
in_cinclude
and
(
definition
if
entry
.
inline_func_in_pxd
or
(
not
entry
.
in_cinclude
and
(
definition
or
entry
.
defined_in_pxd
or
entry
.
visibility
==
'extern'
)):
or
entry
.
defined_in_pxd
or
entry
.
visibility
==
'extern'
)):
if
entry
.
visibility
in
(
'public'
,
'extern'
):
if
entry
.
visibility
==
'public'
:
storage_class
=
"%s "
%
Naming
.
extern_c_macro
dll_linkage
=
"DL_EXPORT"
dll_linkage
=
"DL_EXPORT"
elif
entry
.
visibility
==
'extern'
:
storage_class
=
"%s "
%
Naming
.
extern_c_macro
dll_linkage
=
"DL_IMPORT"
elif
entry
.
visibility
==
'private'
:
storage_class
=
"static "
dll_linkage
=
None
else
:
else
:
storage_class
=
"static "
dll_linkage
=
None
dll_linkage
=
None
type
=
entry
.
type
type
=
entry
.
type
if
not
definition
and
entry
.
defined_in_pxd
:
if
not
definition
and
entry
.
defined_in_pxd
:
type
=
CPtrType
(
type
)
type
=
CPtrType
(
type
)
header
=
type
.
declaration_code
(
entry
.
cname
,
header
=
type
.
declaration_code
(
entry
.
cname
,
dll_linkage
=
dll_linkage
)
dll_linkage
=
dll_linkage
)
if
entry
.
visibility
==
'private'
:
storage_class
=
"static "
elif
entry
.
visibility
==
'public'
:
storage_class
=
""
else
:
storage_class
=
"%s "
%
Naming
.
extern_c_macro
if
entry
.
func_modifiers
:
if
entry
.
func_modifiers
:
modifiers
=
'%s '
%
' '
.
join
([
modifiers
=
"%s "
%
' '
.
join
(
entry
.
func_modifiers
).
upper
()
modifier
.
upper
()
for
modifier
in
entry
.
func_modifiers
])
else
:
else
:
modifiers
=
''
modifiers
=
''
code
.
putln
(
"%s%s%s; /*proto*/"
%
(
code
.
putln
(
"%s%s%s; /*proto*/"
%
(
...
@@ -1806,6 +1827,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -1806,6 +1827,9 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
code
.
putln
(
"/*--- Global init code ---*/"
)
code
.
putln
(
"/*--- Global init code ---*/"
)
self
.
generate_global_init_code
(
env
,
code
)
self
.
generate_global_init_code
(
env
,
code
)
code
.
putln
(
"/*--- Variable export code ---*/"
)
self
.
generate_c_variable_export_code
(
env
,
code
)
code
.
putln
(
"/*--- Function export code ---*/"
)
code
.
putln
(
"/*--- Function export code ---*/"
)
self
.
generate_c_function_export_code
(
env
,
code
)
self
.
generate_c_function_export_code
(
env
,
code
)
...
@@ -1993,6 +2017,18 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
...
@@ -1993,6 +2017,18 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
if
entry
.
type
.
is_pyobject
and
entry
.
used
:
if
entry
.
type
.
is_pyobject
and
entry
.
used
:
code
.
put_init_var_to_py_none
(
entry
,
nanny
=
False
)
code
.
put_init_var_to_py_none
(
entry
,
nanny
=
False
)
def
generate_c_variable_export_code
(
self
,
env
,
code
):
# Generate code to create PyCFunction wrappers for exported C functions.
for
entry
in
env
.
var_entries
:
if
entry
.
api
or
entry
.
defined_in_pxd
:
env
.
use_utility_code
(
voidptr_export_utility_code
)
signature
=
entry
.
type
.
declaration_code
(
""
)
code
.
putln
(
'if (__Pyx_ExportVoidPtr("%s", (void *)&%s, "%s") < 0) %s'
%
(
entry
.
name
,
entry
.
cname
,
signature
,
code
.
error_goto
(
self
.
pos
)))
def
generate_c_function_export_code
(
self
,
env
,
code
):
def
generate_c_function_export_code
(
self
,
env
,
code
):
# Generate code to create PyCFunction wrappers for exported C functions.
# Generate code to create PyCFunction wrappers for exported C functions.
for
entry
in
env
.
cfunc_entries
:
for
entry
in
env
.
cfunc_entries
:
...
@@ -2336,6 +2372,45 @@ bad:
...
@@ -2336,6 +2372,45 @@ bad:
#------------------------------------------------------------------------------------
#------------------------------------------------------------------------------------
voidptr_export_utility_code
=
UtilityCode
(
proto
=
"""
static int __Pyx_ExportVoidPtr(const char *name, void *p, const char *sig); /*proto*/
"""
,
impl
=
r"""
static int __Pyx_ExportVoidPtr(const char *name, void *p, const char *sig) {
PyObject *d = 0;
PyObject *cobj = 0;
d = PyObject_GetAttrString(%(MODULE)s, (char *)"%(API)s");
if (!d) {
PyErr_Clear();
d = PyDict_New();
if (!d)
goto bad;
Py_INCREF(d);
if (PyModule_AddObject(%(MODULE)s, (char *)"%(API)s", d) < 0)
goto bad;
}
#if PY_VERSION_HEX >= 0x02070000 && !(PY_MAJOR_VERSION==3&&PY_MINOR_VERSION==0)
cobj = PyCapsule_New(p, sig, 0);
#else
cobj = PyCObject_FromVoidPtrAndDesc(p, (void *)sig, 0);
#endif
if (!cobj)
goto bad;
if (PyDict_SetItemString(d, name, cobj) < 0)
goto bad;
Py_DECREF(cobj);
Py_DECREF(d);
return 0;
bad:
Py_XDECREF(cobj);
Py_XDECREF(d);
return -1;
}
"""
%
{
'MODULE'
:
Naming
.
module_cname
,
'API'
:
Naming
.
api_name
}
)
function_export_utility_code
=
UtilityCode
(
function_export_utility_code
=
UtilityCode
(
proto
=
"""
proto
=
"""
static int __Pyx_ExportFunction(const char *name, void (*f)(void), const char *sig); /*proto*/
static int __Pyx_ExportFunction(const char *name, void (*f)(void), const char *sig); /*proto*/
...
@@ -2380,6 +2455,62 @@ bad:
...
@@ -2380,6 +2455,62 @@ bad:
"""
%
{
'MODULE'
:
Naming
.
module_cname
,
'API'
:
Naming
.
api_name
}
"""
%
{
'MODULE'
:
Naming
.
module_cname
,
'API'
:
Naming
.
api_name
}
)
)
voidptr_import_utility_code
=
UtilityCode
(
proto
=
"""
static int __Pyx_ImportVoidPtr(PyObject *module, const char *name, void **p, const char *sig); /*proto*/
"""
,
impl
=
"""
#ifndef __PYX_HAVE_RT_ImportVoidPtr
#define __PYX_HAVE_RT_ImportVoidPtr
static int __Pyx_ImportVoidPtr(PyObject *module, const char *name, void **p, const char *sig) {
PyObject *d = 0;
PyObject *cobj = 0;
d = PyObject_GetAttrString(module, (char *)"%(API)s");
if (!d)
goto bad;
cobj = PyDict_GetItemString(d, name);
if (!cobj) {
PyErr_Format(PyExc_ImportError,
"%%s does not export expected C variable %%s",
PyModule_GetName(module), name);
goto bad;
}
#if PY_VERSION_HEX >= 0x02070000 && !(PY_MAJOR_VERSION==3&&PY_MINOR_VERSION==0)
if (!PyCapsule_IsValid(cobj, sig)) {
PyErr_Format(PyExc_TypeError,
"C variable %%s.%%s has wrong signature (expected %%s, got %%s)",
PyModule_GetName(module), name, sig, PyCapsule_GetName(cobj));
goto bad;
}
*p = PyCapsule_GetPointer(cobj, sig);
#else
{const char *desc, *s1, *s2;
desc = (const char *)PyCObject_GetDesc(cobj);
if (!desc)
goto bad;
s1 = desc; s2 = sig;
while (*s1 != '
\
\
0' && *s1 == *s2) { s1++; s2++; }
if (*s1 != *s2) {
PyErr_Format(PyExc_TypeError,
"C variable %%s.%%s has wrong signature (expected %%s, got %%s)",
PyModule_GetName(module), name, sig, desc);
goto bad;
}
*p = PyCObject_AsVoidPtr(cobj);}
#endif
if (!(*p))
goto bad;
Py_DECREF(d);
return 0;
bad:
Py_XDECREF(d);
return -1;
}
#endif
"""
%
dict
(
API
=
Naming
.
api_name
)
)
function_import_utility_code
=
UtilityCode
(
function_import_utility_code
=
UtilityCode
(
proto
=
"""
proto
=
"""
static int __Pyx_ImportFunction(PyObject *module, const char *funcname, void (**f)(void), const char *sig); /*proto*/
static int __Pyx_ImportFunction(PyObject *module, const char *funcname, void (**f)(void), const char *sig); /*proto*/
...
...
Cython/Compiler/Nodes.py
View file @
0a56c99d
...
@@ -970,7 +970,7 @@ class CVarDefNode(StatNode):
...
@@ -970,7 +970,7 @@ class CVarDefNode(StatNode):
error
(
self
.
pos
,
error
(
self
.
pos
,
"Only 'extern' C variable declaration allowed in .pxd file"
)
"Only 'extern' C variable declaration allowed in .pxd file"
)
entry
=
dest_scope
.
declare_var
(
name
,
type
,
declarator
.
pos
,
entry
=
dest_scope
.
declare_var
(
name
,
type
,
declarator
.
pos
,
cname
=
cname
,
visibility
=
visibility
,
is_cdef
=
1
)
cname
=
cname
,
visibility
=
visibility
,
api
=
self
.
api
,
is_cdef
=
1
)
entry
.
needs_property
=
need_property
entry
.
needs_property
=
need_property
...
@@ -980,6 +980,7 @@ class CStructOrUnionDefNode(StatNode):
...
@@ -980,6 +980,7 @@ class CStructOrUnionDefNode(StatNode):
# kind "struct" or "union"
# kind "struct" or "union"
# typedef_flag boolean
# typedef_flag boolean
# visibility "public" or "private"
# visibility "public" or "private"
# api boolean
# in_pxd boolean
# in_pxd boolean
# attributes [CVarDefNode] or None
# attributes [CVarDefNode] or None
# entry Entry
# entry Entry
...
@@ -995,7 +996,8 @@ class CStructOrUnionDefNode(StatNode):
...
@@ -995,7 +996,8 @@ class CStructOrUnionDefNode(StatNode):
scope
=
StructOrUnionScope
(
self
.
name
)
scope
=
StructOrUnionScope
(
self
.
name
)
self
.
entry
=
env
.
declare_struct_or_union
(
self
.
entry
=
env
.
declare_struct_or_union
(
self
.
name
,
self
.
kind
,
scope
,
self
.
typedef_flag
,
self
.
pos
,
self
.
name
,
self
.
kind
,
scope
,
self
.
typedef_flag
,
self
.
pos
,
self
.
cname
,
visibility
=
self
.
visibility
,
packed
=
self
.
packed
)
self
.
cname
,
visibility
=
self
.
visibility
,
api
=
self
.
api
,
packed
=
self
.
packed
)
if
self
.
attributes
is
not
None
:
if
self
.
attributes
is
not
None
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
self
.
entry
.
defined_in_pxd
=
1
self
.
entry
.
defined_in_pxd
=
1
...
@@ -1078,6 +1080,7 @@ class CEnumDefNode(StatNode):
...
@@ -1078,6 +1080,7 @@ class CEnumDefNode(StatNode):
# items [CEnumDefItemNode]
# items [CEnumDefItemNode]
# typedef_flag boolean
# typedef_flag boolean
# visibility "public" or "private"
# visibility "public" or "private"
# api boolean
# in_pxd boolean
# in_pxd boolean
# entry Entry
# entry Entry
...
@@ -1086,7 +1089,7 @@ class CEnumDefNode(StatNode):
...
@@ -1086,7 +1089,7 @@ class CEnumDefNode(StatNode):
def
analyse_declarations
(
self
,
env
):
def
analyse_declarations
(
self
,
env
):
self
.
entry
=
env
.
declare_enum
(
self
.
name
,
self
.
pos
,
self
.
entry
=
env
.
declare_enum
(
self
.
name
,
self
.
pos
,
cname
=
self
.
cname
,
typedef_flag
=
self
.
typedef_flag
,
cname
=
self
.
cname
,
typedef_flag
=
self
.
typedef_flag
,
visibility
=
self
.
visibility
)
visibility
=
self
.
visibility
,
api
=
self
.
api
)
if
self
.
items
is
not
None
:
if
self
.
items
is
not
None
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
self
.
entry
.
defined_in_pxd
=
1
self
.
entry
.
defined_in_pxd
=
1
...
@@ -1097,7 +1100,7 @@ class CEnumDefNode(StatNode):
...
@@ -1097,7 +1100,7 @@ class CEnumDefNode(StatNode):
pass
pass
def
generate_execution_code
(
self
,
code
):
def
generate_execution_code
(
self
,
code
):
if
self
.
visibility
==
'public'
:
if
self
.
visibility
==
'public'
or
self
.
api
:
temp
=
code
.
funcstate
.
allocate_temp
(
PyrexTypes
.
py_object_type
,
manage_ref
=
True
)
temp
=
code
.
funcstate
.
allocate_temp
(
PyrexTypes
.
py_object_type
,
manage_ref
=
True
)
for
item
in
self
.
entry
.
enum_values
:
for
item
in
self
.
entry
.
enum_values
:
code
.
putln
(
"%s = PyInt_FromLong(%s); %s"
%
(
code
.
putln
(
"%s = PyInt_FromLong(%s); %s"
%
(
...
@@ -1129,7 +1132,7 @@ class CEnumDefItemNode(StatNode):
...
@@ -1129,7 +1132,7 @@ class CEnumDefItemNode(StatNode):
self
.
value
.
analyse_const_expression
(
env
)
self
.
value
.
analyse_const_expression
(
env
)
entry
=
env
.
declare_const
(
self
.
name
,
enum_entry
.
type
,
entry
=
env
.
declare_const
(
self
.
name
,
enum_entry
.
type
,
self
.
value
,
self
.
pos
,
cname
=
self
.
cname
,
self
.
value
,
self
.
pos
,
cname
=
self
.
cname
,
visibility
=
enum_entry
.
visibility
)
visibility
=
enum_entry
.
visibility
,
api
=
enum_entry
.
api
)
enum_entry
.
enum_values
.
append
(
entry
)
enum_entry
.
enum_values
.
append
(
entry
)
...
@@ -1137,6 +1140,7 @@ class CTypeDefNode(StatNode):
...
@@ -1137,6 +1140,7 @@ class CTypeDefNode(StatNode):
# base_type CBaseTypeNode
# base_type CBaseTypeNode
# declarator CDeclaratorNode
# declarator CDeclaratorNode
# visibility "public" or "private"
# visibility "public" or "private"
# api boolean
# in_pxd boolean
# in_pxd boolean
child_attrs
=
[
"base_type"
,
"declarator"
]
child_attrs
=
[
"base_type"
,
"declarator"
]
...
@@ -1147,7 +1151,7 @@ class CTypeDefNode(StatNode):
...
@@ -1147,7 +1151,7 @@ class CTypeDefNode(StatNode):
name
=
name_declarator
.
name
name
=
name_declarator
.
name
cname
=
name_declarator
.
cname
cname
=
name_declarator
.
cname
entry
=
env
.
declare_typedef
(
name
,
type
,
self
.
pos
,
entry
=
env
.
declare_typedef
(
name
,
type
,
self
.
pos
,
cname
=
cname
,
visibility
=
self
.
visibility
)
cname
=
cname
,
visibility
=
self
.
visibility
,
api
=
self
.
api
)
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
entry
.
defined_in_pxd
=
1
entry
.
defined_in_pxd
=
1
...
@@ -1740,7 +1744,6 @@ class CFuncDefNode(FuncDefNode):
...
@@ -1740,7 +1744,6 @@ class CFuncDefNode(FuncDefNode):
def
generate_function_header
(
self
,
code
,
with_pymethdef
,
with_opt_args
=
1
,
with_dispatch
=
1
,
cname
=
None
):
def
generate_function_header
(
self
,
code
,
with_pymethdef
,
with_opt_args
=
1
,
with_dispatch
=
1
,
cname
=
None
):
arg_decls
=
[]
arg_decls
=
[]
type
=
self
.
type
type
=
self
.
type
visibility
=
self
.
entry
.
visibility
for
arg
in
type
.
args
[:
len
(
type
.
args
)
-
type
.
optional_arg_count
]:
for
arg
in
type
.
args
[:
len
(
type
.
args
)
-
type
.
optional_arg_count
]:
arg_decls
.
append
(
arg
.
declaration_code
())
arg_decls
.
append
(
arg
.
declaration_code
())
if
with_dispatch
and
self
.
overridable
:
if
with_dispatch
and
self
.
overridable
:
...
@@ -1754,24 +1757,20 @@ class CFuncDefNode(FuncDefNode):
...
@@ -1754,24 +1757,20 @@ class CFuncDefNode(FuncDefNode):
if
cname
is
None
:
if
cname
is
None
:
cname
=
self
.
entry
.
func_cname
cname
=
self
.
entry
.
func_cname
entity
=
type
.
function_header_code
(
cname
,
', '
.
join
(
arg_decls
))
entity
=
type
.
function_header_code
(
cname
,
', '
.
join
(
arg_decls
))
if
visibility
==
'public
'
:
if
self
.
entry
.
visibility
==
'private
'
:
dll_linkage
=
"DL_EXPORT
"
storage_class
=
"static
"
else
:
else
:
dll_linkage
=
None
header
=
self
.
return_type
.
declaration_code
(
entity
,
dll_linkage
=
dll_linkage
)
if
visibility
==
'extern'
:
storage_class
=
"%s "
%
Naming
.
extern_c_macro
elif
visibility
==
'public'
:
storage_class
=
""
storage_class
=
""
else
:
dll_linkage
=
None
storage_class
=
"static
"
modifiers
=
"
"
if
'inline'
in
self
.
modifiers
:
if
'inline'
in
self
.
modifiers
:
self
.
modifiers
[
self
.
modifiers
.
index
(
'inline'
)]
=
'cython_inline'
self
.
modifiers
[
self
.
modifiers
.
index
(
'inline'
)]
=
'cython_inline'
code
.
putln
(
"%s%s %s {"
%
(
if
self
.
modifiers
:
storage_class
,
modifiers
=
"%s "
%
' '
.
join
(
self
.
modifiers
).
upper
()
' '
.
join
(
self
.
modifiers
).
upper
(),
# macro forms
header
))
header
=
self
.
return_type
.
declaration_code
(
entity
,
dll_linkage
=
dll_linkage
)
#print (storage_class, modifiers, header)
code
.
putln
(
"%s%s%s {"
%
(
storage_class
,
modifiers
,
header
))
def
generate_argument_declarations
(
self
,
env
,
code
):
def
generate_argument_declarations
(
self
,
env
,
code
):
for
arg
in
self
.
args
:
for
arg
in
self
.
args
:
...
...
Cython/Compiler/Parsing.py
View file @
0a56c99d
...
@@ -2420,7 +2420,7 @@ def p_c_enum_definition(s, pos, ctx):
...
@@ -2420,7 +2420,7 @@ def p_c_enum_definition(s, pos, ctx):
return
Nodes
.
CEnumDefNode
(
return
Nodes
.
CEnumDefNode
(
pos
,
name
=
name
,
cname
=
cname
,
items
=
items
,
pos
,
name
=
name
,
cname
=
cname
,
items
=
items
,
typedef_flag
=
ctx
.
typedef_flag
,
visibility
=
ctx
.
visibility
,
typedef_flag
=
ctx
.
typedef_flag
,
visibility
=
ctx
.
visibility
,
in_pxd
=
ctx
.
level
==
'module_pxd'
)
api
=
ctx
.
api
,
in_pxd
=
ctx
.
level
==
'module_pxd'
)
def
p_c_enum_line
(
s
,
ctx
,
items
):
def
p_c_enum_line
(
s
,
ctx
,
items
):
if
s
.
sy
!=
'pass'
:
if
s
.
sy
!=
'pass'
:
...
@@ -2481,7 +2481,7 @@ def p_c_struct_or_union_definition(s, pos, ctx):
...
@@ -2481,7 +2481,7 @@ def p_c_struct_or_union_definition(s, pos, ctx):
return
Nodes
.
CStructOrUnionDefNode
(
pos
,
return
Nodes
.
CStructOrUnionDefNode
(
pos
,
name
=
name
,
cname
=
cname
,
kind
=
kind
,
attributes
=
attributes
,
name
=
name
,
cname
=
cname
,
kind
=
kind
,
attributes
=
attributes
,
typedef_flag
=
ctx
.
typedef_flag
,
visibility
=
ctx
.
visibility
,
typedef_flag
=
ctx
.
typedef_flag
,
visibility
=
ctx
.
visibility
,
in_pxd
=
ctx
.
level
==
'module_pxd'
,
packed
=
packed
)
api
=
ctx
.
api
,
in_pxd
=
ctx
.
level
==
'module_pxd'
,
packed
=
packed
)
def
p_visibility
(
s
,
prev_visibility
):
def
p_visibility
(
s
,
prev_visibility
):
pos
=
s
.
position
()
pos
=
s
.
position
()
...
@@ -2566,7 +2566,8 @@ def p_ctypedef_statement(s, ctx):
...
@@ -2566,7 +2566,8 @@ def p_ctypedef_statement(s, ctx):
s
.
expect_newline
(
"Syntax error in ctypedef statement"
)
s
.
expect_newline
(
"Syntax error in ctypedef statement"
)
return
Nodes
.
CTypeDefNode
(
return
Nodes
.
CTypeDefNode
(
pos
,
base_type
=
base_type
,
pos
,
base_type
=
base_type
,
declarator
=
declarator
,
visibility
=
visibility
,
declarator
=
declarator
,
visibility
=
visibility
,
api
=
api
,
in_pxd
=
ctx
.
level
==
'module_pxd'
)
in_pxd
=
ctx
.
level
==
'module_pxd'
)
def
p_decorators
(
s
):
def
p_decorators
(
s
):
...
@@ -2693,8 +2694,8 @@ def p_c_class_definition(s, pos, ctx):
...
@@ -2693,8 +2694,8 @@ def p_c_class_definition(s, pos, ctx):
base_class_module
=
"."
.
join
(
base_class_path
[:
-
1
])
base_class_module
=
"."
.
join
(
base_class_path
[:
-
1
])
base_class_name
=
base_class_path
[
-
1
]
base_class_name
=
base_class_path
[
-
1
]
if
s
.
sy
==
'['
:
if
s
.
sy
==
'['
:
if
ctx
.
visibility
not
in
(
'public'
,
'extern'
):
if
ctx
.
visibility
not
in
(
'public'
,
'extern'
)
and
not
ctx
.
api
:
error
(
s
.
position
(),
"Name options only allowed for 'public' or 'extern' C class"
)
error
(
s
.
position
(),
"Name options only allowed for 'public'
, 'api',
or 'extern' C class"
)
objstruct_name
,
typeobj_name
=
p_c_class_options
(
s
)
objstruct_name
,
typeobj_name
=
p_c_class_options
(
s
)
if
s
.
sy
==
':'
:
if
s
.
sy
==
':'
:
if
ctx
.
level
==
'module_pxd'
:
if
ctx
.
level
==
'module_pxd'
:
...
@@ -2718,7 +2719,10 @@ def p_c_class_definition(s, pos, ctx):
...
@@ -2718,7 +2719,10 @@ def p_c_class_definition(s, pos, ctx):
error
(
pos
,
"Type object name specification required for 'public' C class"
)
error
(
pos
,
"Type object name specification required for 'public' C class"
)
elif
ctx
.
visibility
==
'private'
:
elif
ctx
.
visibility
==
'private'
:
if
ctx
.
api
:
if
ctx
.
api
:
error
(
pos
,
"Only 'public' C class can be declared 'api'"
)
if
not
objstruct_name
:
error
(
pos
,
"Object struct name specification required for 'api' C class"
)
if
not
typeobj_name
:
error
(
pos
,
"Type object name specification required for 'api' C class"
)
else
:
else
:
error
(
pos
,
"Invalid class visibility '%s'"
%
ctx
.
visibility
)
error
(
pos
,
"Invalid class visibility '%s'"
%
ctx
.
visibility
)
return
Nodes
.
CClassDefNode
(
pos
,
return
Nodes
.
CClassDefNode
(
pos
,
...
...
Cython/Compiler/PyrexTypes.py
View file @
0a56c99d
...
@@ -1190,8 +1190,8 @@ class CComplexType(CNumericType):
...
@@ -1190,8 +1190,8 @@ class CComplexType(CNumericType):
visibility
=
"extern"
)
visibility
=
"extern"
)
scope
.
parent_type
=
self
scope
.
parent_type
=
self
scope
.
directives
=
{}
scope
.
directives
=
{}
scope
.
declare_var
(
"real"
,
self
.
real_type
,
None
,
"real"
,
is_cdef
=
True
)
scope
.
declare_var
(
"real"
,
self
.
real_type
,
None
,
cname
=
"real"
,
is_cdef
=
True
)
scope
.
declare_var
(
"imag"
,
self
.
real_type
,
None
,
"imag"
,
is_cdef
=
True
)
scope
.
declare_var
(
"imag"
,
self
.
real_type
,
None
,
cname
=
"imag"
,
is_cdef
=
True
)
entry
=
scope
.
declare_cfunction
(
entry
=
scope
.
declare_cfunction
(
"conjugate"
,
"conjugate"
,
CFuncType
(
self
,
[
CFuncTypeArg
(
"self"
,
self
,
None
)],
nogil
=
True
),
CFuncType
(
self
,
[
CFuncTypeArg
(
"self"
,
self
,
None
)],
nogil
=
True
),
...
...
Cython/Compiler/Symtab.py
View file @
0a56c99d
...
@@ -361,10 +361,10 @@ class Scope(object):
...
@@ -361,10 +361,10 @@ class Scope(object):
def qualify_name(self, name):
def qualify_name(self, name):
return EncodedString("
%
s
.
%
s
" % (self.qualified_name, name))
return EncodedString("
%
s
.
%
s
" % (self.qualified_name, name))
def declare_const(self, name, type, value, pos, cname = None, visibility = 'private'):
def declare_const(self, name, type, value, pos, cname = None, visibility = 'private'
, api = 0
):
# Add an entry for a named constant.
# Add an entry for a named constant.
if not cname:
if not cname:
if self.in_cinclude or
visibility == 'public'
:
if self.in_cinclude or
(visibility == 'public' or api)
:
cname = name
cname = name
else:
else:
cname = self.mangle(Naming.enum_prefix, name)
cname = self.mangle(Naming.enum_prefix, name)
...
@@ -374,21 +374,22 @@ class Scope(object):
...
@@ -374,21 +374,22 @@ class Scope(object):
return entry
return entry
def declare_type(self, name, type, pos,
def declare_type(self, name, type, pos,
cname = None, visibility = 'private', defining = 1, shadow = 0):
cname = None, visibility = 'private',
api = 0,
defining = 1, shadow = 0):
# Add an entry for a type definition.
# Add an entry for a type definition.
if not cname:
if not cname:
cname = name
cname = name
entry = self.declare(name, cname, type, pos, visibility, shadow)
entry = self.declare(name, cname, type, pos, visibility, shadow)
entry.is_type = 1
entry.is_type = 1
entry.api = api
if defining:
if defining:
self.type_entries.append(entry)
self.type_entries.append(entry)
# here we would set as_variable to an object representing this type
# here we would set as_variable to an object representing this type
return entry
return entry
def declare_typedef(self, name, base_type, pos, cname = None,
def declare_typedef(self, name, base_type, pos, cname = None,
visibility = 'private'
):
visibility = 'private', api = 0
):
if not cname:
if not cname:
if self.in_cinclude or
visibility == 'public'
:
if self.in_cinclude or
(visibility == 'public' or api)
:
cname = name
cname = name
else:
else:
cname = self.mangle(Naming.type_prefix, name)
cname = self.mangle(Naming.type_prefix, name)
...
@@ -398,16 +399,18 @@ class Scope(object):
...
@@ -398,16 +399,18 @@ class Scope(object):
except ValueError, e:
except ValueError, e:
error(pos, e.args[0])
error(pos, e.args[0])
type = PyrexTypes.error_type
type = PyrexTypes.error_type
entry = self.declare_type(name, type, pos, cname, visibility)
entry = self.declare_type(name, type, pos, cname,
visibility = visibility, api = api)
type.qualified_name = entry.qualified_name
type.qualified_name = entry.qualified_name
return entry
return entry
def declare_struct_or_union(self, name, kind, scope,
def declare_struct_or_union(self, name, kind, scope,
typedef_flag, pos, cname = None, visibility = 'private',
typedef_flag, pos, cname = None,
visibility = 'private', api = 0,
packed = False):
packed = False):
# Add an entry for a struct or union definition.
# Add an entry for a struct or union definition.
if not cname:
if not cname:
if self.in_cinclude or
visibility == 'public'
:
if self.in_cinclude or
(visibility == 'public' or api)
:
cname = name
cname = name
else:
else:
cname = self.mangle(Naming.type_prefix, name)
cname = self.mangle(Naming.type_prefix, name)
...
@@ -416,7 +419,8 @@ class Scope(object):
...
@@ -416,7 +419,8 @@ class Scope(object):
type = PyrexTypes.CStructOrUnionType(
type = PyrexTypes.CStructOrUnionType(
name, kind, scope, typedef_flag, cname, packed)
name, kind, scope, typedef_flag, cname, packed)
entry = self.declare_type(name, type, pos, cname,
entry = self.declare_type(name, type, pos, cname,
visibility = visibility, defining = scope is not None)
visibility = visibility, api = api,
defining = scope is not None)
self.sue_entries.append(entry)
self.sue_entries.append(entry)
type.entry = entry
type.entry = entry
else:
else:
...
@@ -484,10 +488,10 @@ class Scope(object):
...
@@ -484,10 +488,10 @@ class Scope(object):
entry.name, entry.visibility))
entry.name, entry.visibility))
def declare_enum(self, name, pos, cname, typedef_flag,
def declare_enum(self, name, pos, cname, typedef_flag,
visibility = 'private'):
visibility = 'private'
, api = 0
):
if name:
if name:
if not cname:
if not cname:
if self.in_cinclude or
visibility == 'public'
:
if self.in_cinclude or
(visibility == 'public' or api)
:
cname = name
cname = name
else:
else:
cname = self.mangle(Naming.type_prefix, name)
cname = self.mangle(Naming.type_prefix, name)
...
@@ -495,13 +499,13 @@ class Scope(object):
...
@@ -495,13 +499,13 @@ class Scope(object):
else:
else:
type = PyrexTypes.c_anon_enum_type
type = PyrexTypes.c_anon_enum_type
entry = self.declare_type(name, type, pos, cname = cname,
entry = self.declare_type(name, type, pos, cname = cname,
visibility = visibility)
visibility = visibility
, api = api
)
entry.enum_values = []
entry.enum_values = []
self.sue_entries.append(entry)
self.sue_entries.append(entry)
return entry
return entry
def declare_var(self, name, type, pos,
def declare_var(self, name, type, pos,
cname = None, visibility = 'private'
, is_cdef = 0):
cname = None, visibility = 'private', api = 0
, is_cdef = 0):
# Add an entry for a variable.
# Add an entry for a variable.
if not cname:
if not cname:
if visibility != 'private':
if visibility != 'private':
...
@@ -514,6 +518,7 @@ class Scope(object):
...
@@ -514,6 +518,7 @@ class Scope(object):
error(pos, "
C
++
class
must
have
a
default
constructor
to
be
stack
allocated
")
error(pos, "
C
++
class
must
have
a
default
constructor
to
be
stack
allocated
")
entry = self.declare(name, cname, type, pos, visibility)
entry = self.declare(name, cname, type, pos, visibility)
entry.is_variable = 1
entry.is_variable = 1
entry.api = api
self.control_flow.set_state((), (name, 'initialized'), False)
self.control_flow.set_state((), (name, 'initialized'), False)
return entry
return entry
...
@@ -995,13 +1000,13 @@ class ModuleScope(Scope):
...
@@ -995,13 +1000,13 @@ class ModuleScope(Scope):
return entry
return entry
def declare_var(self, name, type, pos,
def declare_var(self, name, type, pos,
cname = None, visibility = 'private'
, is_cdef = 0):
cname = None, visibility = 'private', api = 0
, is_cdef = 0):
# Add an entry for a global variable. If it is a Python
# Add an entry for a global variable. If it is a Python
# object type, and not declared with cdef, it will live
# object type, and not declared with cdef, it will live
# in the module dictionary, otherwise it will be a C
# in the module dictionary, otherwise it will be a C
# global variable.
# global variable.
entry = Scope.declare_var(self, name, type, pos,
entry = Scope.declare_var(self, name, type, pos,
cname, visibility,
is_cdef)
cname=cname, visibility=visibility, api=api, is_cdef=
is_cdef)
if not visibility in ('private', 'public', 'extern'):
if not visibility in ('private', 'public', 'extern'):
error(pos, "
Module
-
level
variable
cannot
be
declared
%
s
" % visibility)
error(pos, "
Module
-
level
variable
cannot
be
declared
%
s
" % visibility)
if not is_cdef:
if not is_cdef:
...
@@ -1035,8 +1040,8 @@ class ModuleScope(Scope):
...
@@ -1035,8 +1040,8 @@ class ModuleScope(Scope):
# the non-typedef struct internally to avoid needing forward
# the non-typedef struct internally to avoid needing forward
# declarations for anonymous structs.
# declarations for anonymous structs.
if typedef_flag and visibility != 'extern':
if typedef_flag and visibility != 'extern':
if
visibility != 'public'
:
if
not (visibility == 'public' or api)
:
warning(pos, "
ctypedef
only
valid
for
public
and
extern
classes
", 2)
warning(pos, "
ctypedef
only
valid
for
'extern'
,
'public'
,
and
'api'
", 2)
objtypedef_cname = objstruct_cname
objtypedef_cname = objstruct_cname
typedef_flag = 0
typedef_flag = 0
else:
else:
...
@@ -1283,12 +1288,12 @@ class LocalScope(Scope):
...
@@ -1283,12 +1288,12 @@ class LocalScope(Scope):
return
entry
return
entry
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
is_cdef
=
0
):
cname
=
None
,
visibility
=
'private'
,
api
=
0
,
is_cdef
=
0
):
# Add an entry for a local variable.
# Add an entry for a local variable.
if
visibility
in
(
'public'
,
'readonly'
):
if
visibility
in
(
'public'
,
'readonly'
):
error
(
pos
,
"Local variable cannot be declared %s"
%
visibility
)
error
(
pos
,
"Local variable cannot be declared %s"
%
visibility
)
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
cname
,
visibility
,
is_cdef
)
cname
=
cname
,
visibility
=
visibility
,
api
=
api
,
is_cdef
=
is_cdef
)
if
type
.
is_pyobject
and
not
Options
.
init_local_none
:
if
type
.
is_pyobject
and
not
Options
.
init_local_none
:
entry
.
init
=
"0"
entry
.
init
=
"0"
entry
.
init_to_none
=
(
type
.
is_pyobject
or
type
.
is_unspecified
)
and
Options
.
init_local_none
entry
.
init_to_none
=
(
type
.
is_pyobject
or
type
.
is_unspecified
)
and
Options
.
init_local_none
...
@@ -1354,7 +1359,7 @@ class GeneratorExpressionScope(Scope):
...
@@ -1354,7 +1359,7 @@ class GeneratorExpressionScope(Scope):
return
'%s%s'
%
(
self
.
genexp_prefix
,
self
.
parent_scope
.
mangle
(
prefix
,
name
))
return
'%s%s'
%
(
self
.
genexp_prefix
,
self
.
parent_scope
.
mangle
(
prefix
,
name
))
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
is_cdef
=
True
):
cname
=
None
,
visibility
=
'private'
,
api
=
0
,
is_cdef
=
True
):
if
type
is
unspecified_type
:
if
type
is
unspecified_type
:
# if the outer scope defines a type for this variable, inherit it
# if the outer scope defines a type for this variable, inherit it
outer_entry
=
self
.
outer_scope
.
lookup
(
name
)
outer_entry
=
self
.
outer_scope
.
lookup
(
name
)
...
@@ -1397,7 +1402,7 @@ class StructOrUnionScope(Scope):
...
@@ -1397,7 +1402,7 @@ class StructOrUnionScope(Scope):
Scope
.
__init__
(
self
,
name
,
None
,
None
)
Scope
.
__init__
(
self
,
name
,
None
,
None
)
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
is_cdef
=
0
,
allow_pyobject
=
0
):
cname
=
None
,
visibility
=
'private'
,
api
=
0
,
is_cdef
=
0
,
allow_pyobject
=
0
):
# Add an entry for an attribute.
# Add an entry for an attribute.
if
not
cname
:
if
not
cname
:
cname
=
name
cname
=
name
...
@@ -1419,7 +1424,8 @@ class StructOrUnionScope(Scope):
...
@@ -1419,7 +1424,8 @@ class StructOrUnionScope(Scope):
def
declare_cfunction
(
self
,
name
,
type
,
pos
,
def
declare_cfunction
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
defining
=
0
,
cname
=
None
,
visibility
=
'private'
,
defining
=
0
,
api
=
0
,
in_pxd
=
0
,
modifiers
=
()):
# currently no utility code ...
api
=
0
,
in_pxd
=
0
,
modifiers
=
()):
# currently no utility code ...
return
self
.
declare_var
(
name
,
type
,
pos
,
cname
,
visibility
)
return
self
.
declare_var
(
name
,
type
,
pos
,
cname
=
cname
,
visibility
=
visibility
)
class
ClassScope
(
Scope
):
class
ClassScope
(
Scope
):
# Abstract base class for namespace of
# Abstract base class for namespace of
...
@@ -1463,12 +1469,12 @@ class PyClassScope(ClassScope):
...
@@ -1463,12 +1469,12 @@ class PyClassScope(ClassScope):
is_py_class_scope
=
1
is_py_class_scope
=
1
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
is_cdef
=
0
):
cname
=
None
,
visibility
=
'private'
,
api
=
0
,
is_cdef
=
0
):
if
type
is
unspecified_type
:
if
type
is
unspecified_type
:
type
=
py_object_type
type
=
py_object_type
# Add an entry for a class attribute.
# Add an entry for a class attribute.
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
cname
,
visibility
,
is_cdef
)
cname
=
cname
,
visibility
=
visibility
,
api
=
api
,
is_cdef
=
is_cdef
)
entry
.
is_pyglobal
=
1
entry
.
is_pyglobal
=
1
entry
.
is_pyclass_attr
=
1
entry
.
is_pyclass_attr
=
1
return
entry
return
entry
...
@@ -1513,7 +1519,7 @@ class CClassScope(ClassScope):
...
@@ -1513,7 +1519,7 @@ class CClassScope(ClassScope):
self
.
parent_type
.
base_type
.
scope
.
needs_gc
())
self
.
parent_type
.
base_type
.
scope
.
needs_gc
())
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'private'
,
is_cdef
=
0
):
cname
=
None
,
visibility
=
'private'
,
api
=
0
,
is_cdef
=
0
):
if
is_cdef
:
if
is_cdef
:
# Add an entry for an attribute.
# Add an entry for an attribute.
if
self
.
defined
:
if
self
.
defined
:
...
@@ -1553,7 +1559,7 @@ class CClassScope(ClassScope):
...
@@ -1553,7 +1559,7 @@ class CClassScope(ClassScope):
type
=
py_object_type
type
=
py_object_type
# Add an entry for a class attribute.
# Add an entry for a class attribute.
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
entry
=
Scope
.
declare_var
(
self
,
name
,
type
,
pos
,
cname
,
visibility
,
is_cdef
)
cname
=
cname
,
visibility
=
visibility
,
api
=
api
,
is_cdef
=
is_cdef
)
entry
.
is_member
=
1
entry
.
is_member
=
1
entry
.
is_pyglobal
=
1
# xxx: is_pyglobal changes behaviour in so many places that
entry
.
is_pyglobal
=
1
# xxx: is_pyglobal changes behaviour in so many places that
# I keep it in for now. is_member should be enough
# I keep it in for now. is_member should be enough
...
@@ -1569,7 +1575,8 @@ class CClassScope(ClassScope):
...
@@ -1569,7 +1575,8 @@ class CClassScope(ClassScope):
if
name
==
"__new__"
:
if
name
==
"__new__"
:
error
(
pos
,
"__new__ method of extension type will change semantics "
error
(
pos
,
"__new__ method of extension type will change semantics "
"in a future version of Pyrex and Cython. Use __cinit__ instead."
)
"in a future version of Pyrex and Cython. Use __cinit__ instead."
)
entry
=
self
.
declare_var
(
name
,
py_object_type
,
pos
,
visibility
=
'extern'
)
entry
=
self
.
declare_var
(
name
,
py_object_type
,
pos
,
visibility
=
'extern'
)
special_sig
=
get_special_method_signature
(
name
)
special_sig
=
get_special_method_signature
(
name
)
if
special_sig
:
if
special_sig
:
# Special methods get put in the method table with a particular
# Special methods get put in the method table with a particular
...
@@ -1694,7 +1701,8 @@ class CppClassScope(Scope):
...
@@ -1694,7 +1701,8 @@ class CppClassScope(Scope):
self
.
inherited_var_entries
=
[]
self
.
inherited_var_entries
=
[]
def
declare_var
(
self
,
name
,
type
,
pos
,
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'extern'
,
is_cdef
=
0
,
allow_pyobject
=
0
):
cname
=
None
,
visibility
=
'extern'
,
api
=
0
,
is_cdef
=
0
,
allow_pyobject
=
0
):
# Add an entry for an attribute.
# Add an entry for an attribute.
if
not
cname
:
if
not
cname
:
cname
=
name
cname
=
name
...
@@ -1735,15 +1743,16 @@ class CppClassScope(Scope):
...
@@ -1735,15 +1743,16 @@ class CppClassScope(Scope):
error
(
pos
,
"no matching function for call to %s::%s()"
%
error
(
pos
,
"no matching function for call to %s::%s()"
%
(
self
.
default_constructor
,
self
.
default_constructor
))
(
self
.
default_constructor
,
self
.
default_constructor
))
def
declare_cfunction
(
self
,
name
,
type
,
pos
,
def
declare_cfunction
(
self
,
name
,
type
,
pos
,
cname
=
None
,
cname
=
None
,
visibility
=
'extern'
,
defining
=
0
,
visibility
=
'extern'
,
api
=
0
,
defining
=
0
,
api
=
0
,
in_pxd
=
0
,
modifiers
=
(),
utility_code
=
None
):
in_pxd
=
0
,
modifiers
=
(),
utility_code
=
None
):
if
name
==
self
.
name
.
split
(
'::'
)[
-
1
]
and
cname
is
None
:
if
name
==
self
.
name
.
split
(
'::'
)[
-
1
]
and
cname
is
None
:
self
.
check_base_default_constructor
(
pos
)
self
.
check_base_default_constructor
(
pos
)
name
=
'<init>'
name
=
'<init>'
type
.
return_type
=
self
.
lookup
(
self
.
name
).
type
type
.
return_type
=
self
.
lookup
(
self
.
name
).
type
prev_entry
=
self
.
lookup_here
(
name
)
prev_entry
=
self
.
lookup_here
(
name
)
entry
=
self
.
declare_var
(
name
,
type
,
pos
,
cname
,
visibility
)
entry
=
self
.
declare_var
(
name
,
type
,
pos
,
cname
=
cname
,
visibility
=
visibility
)
if
prev_entry
:
if
prev_entry
:
entry
.
overloaded_alternatives
=
prev_entry
.
all_alternatives
()
entry
.
overloaded_alternatives
=
prev_entry
.
all_alternatives
()
entry
.
utility_code
=
utility_code
entry
.
utility_code
=
utility_code
...
@@ -1768,7 +1777,8 @@ class CppClassScope(Scope):
...
@@ -1768,7 +1777,8 @@ class CppClassScope(Scope):
for
base_entry
in
base_scope
.
cfunc_entries
:
for
base_entry
in
base_scope
.
cfunc_entries
:
entry
=
self
.
declare_cfunction
(
base_entry
.
name
,
base_entry
.
type
,
entry
=
self
.
declare_cfunction
(
base_entry
.
name
,
base_entry
.
type
,
base_entry
.
pos
,
base_entry
.
cname
,
base_entry
.
pos
,
base_entry
.
cname
,
base_entry
.
visibility
,
base_entry
.
func_modifiers
,
base_entry
.
visibility
,
0
,
modifiers
=
base_entry
.
func_modifiers
,
utility_code
=
base_entry
.
utility_code
)
utility_code
=
base_entry
.
utility_code
)
entry
.
is_inherited
=
1
entry
.
is_inherited
=
1
...
...
tests/compile/a_capi.pyx
View file @
0a56c99d
...
@@ -11,6 +11,12 @@ cdef public class C[type C_Type, object C_Obj]:
...
@@ -11,6 +11,12 @@ cdef public class C[type C_Type, object C_Obj]:
cdef
public
Zax
*
blarg
cdef
public
Zax
*
blarg
cdef
public
C
c_pub
=
C
()
cdef
api
C
c_api
=
C
()
cdef
public
dict
o_pub
=
C
()
cdef
api
list
o_api
=
C
()
cdef
api
float
f
(
Foo
*
x
):
cdef
api
float
f
(
Foo
*
x
):
pass
pass
...
...
tests/compile/publicapi_api.pyx
0 → 100644
View file @
0a56c99d
# --
ctypedef
int
Int0
ctypedef
api
int
Int1
ctypedef
enum
EnumA0
:
EA0
ctypedef
api
enum
EnumA1
:
EA1
cdef
enum
EnumB0
:
EB0
=
0
cdef
api
enum
EnumB1
:
EB1
=
1
cdef
Int0
i0
=
0
cdef
EnumA0
ea0
=
EA0
cdef
EnumB0
eb0
=
EB0
cdef
api
Int1
i1
=
0
cdef
api
EnumA1
ea1
=
EA1
cdef
api
EnumB1
eb1
=
EB1
# --
ctypedef
struct
StructA0
:
int
SA0
ctypedef
api
struct
StructA1
:
int
SA1
cdef
struct
StructB0
:
int
SB0
cdef
api
struct
StructB1
:
int
SB1
cdef
StructA0
sa0
=
{
'SA0'
:
0
}
cdef
StructB0
sb0
=
{
'SB0'
:
2
}
cdef
api
StructA1
sa1
=
{
'SA1'
:
1
}
cdef
api
StructB1
sb1
=
{
'SB1'
:
3
}
# --
ctypedef
class
Foo0
:
pass
ctypedef
api
class
Foo1
[
type
PyFoo1_Type
,
object
PyFoo1_Object
]:
pass
cdef
class
Bar0
:
pass
cdef
api
class
Bar1
[
type
PyBar1_Type
,
object
PyBar1_Object
]:
pass
cdef
Foo0
f0
=
None
cdef
Bar0
b0
=
None
cdef
api
Foo1
f1
=
None
cdef
api
Bar1
b1
=
None
# --
cdef
void
bar0
():
pass
cdef
api
void
bar1
():
pass
cdef
void
*
spam0
(
object
o
)
except
NULL
:
return
NULL
cdef
api
void
*
spam1
(
object
o
)
except
NULL
:
return
NULL
bar0
()
bar1
()
spam0
(
None
)
spam1
(
None
)
# --
tests/compile/publicapi_mix.pyx
0 → 100644
View file @
0a56c99d
# --
ctypedef
int
Int0
ctypedef
public
int
Int1
ctypedef
api
int
Int2
ctypedef
public
api
int
Int3
ctypedef
enum
EnumA0
:
EA0
ctypedef
public
enum
EnumA1
:
EA1
ctypedef
api
enum
EnumA2
:
EA2
ctypedef
public
api
enum
EnumA3
:
EA3
cdef
enum
EnumB0
:
EB0
=
0
cdef
public
enum
EnumB1
:
EB1
=
1
cdef
api
enum
EnumB2
:
EB2
=
2
cdef
public
api
enum
EnumB3
:
EB3
=
3
# --
ctypedef
struct
StructA0
:
int
SA0
ctypedef
public
struct
StructA1
:
int
SA1
ctypedef
api
struct
StructA2
:
int
SA2
ctypedef
public
api
struct
StructA3
:
int
SA3
cdef
struct
StructB0
:
int
SB0
cdef
public
struct
StructB1
:
int
SB1
cdef
api
struct
StructB2
:
int
SB2
cdef
public
api
struct
StructB3
:
int
SB3
# --
ctypedef
class
Foo0
:
pass
ctypedef
public
class
Foo1
[
type
PyFoo1_Type
,
object
PyFoo1_Object
]:
pass
ctypedef
api
class
Foo2
[
type
PyFoo2_Type
,
object
PyFoo2_Object
]:
pass
ctypedef
public
api
class
Foo3
[
type
PyFoo3_Type
,
object
PyFoo3_Object
]:
pass
cdef
class
Bar0
:
pass
cdef
public
class
Bar1
[
type
PyBar1_Type
,
object
PyBar1_Object
]:
pass
cdef
api
class
Bar2
[
type
PyBar2_Type
,
object
PyBar2_Object
]:
pass
cdef
public
api
class
Bar3
[
type
PyBar3_Type
,
object
PyBar3_Object
]:
pass
# --
cdef
void
bar0
():
pass
cdef
public
void
bar1
():
pass
cdef
api
void
bar2
():
pass
cdef
public
api
void
bar3
():
pass
cdef
void
*
spam0
(
object
o
)
except
NULL
:
return
NULL
cdef
public
void
*
spam1
(
object
o
)
except
NULL
:
return
NULL
cdef
api
void
*
spam2
(
object
o
)
except
NULL
:
return
NULL
cdef
public
api
void
*
spam3
(
object
o
)
except
NULL
:
return
NULL
bar0
()
spam0
(
None
)
# --
cdef
double
d0
=
0
cdef
public
double
d1
=
1
cdef
api
double
d2
=
2
cdef
public
api
double
d3
=
3
cdef
object
o0
=
None
cdef
public
object
o1
=
None
cdef
api
object
o2
=
None
cdef
public
api
object
o3
=
None
# --
tests/compile/publicapi_pub.pyx
0 → 100644
View file @
0a56c99d
# --
ctypedef
int
Int0
ctypedef
public
int
Int1
ctypedef
enum
EnumA0
:
EA0
ctypedef
public
enum
EnumA1
:
EA1
cdef
enum
EnumB0
:
EB0
=
0
cdef
public
enum
EnumB1
:
EB1
=
1
cdef
Int0
i0
=
0
cdef
EnumA0
ea0
=
EA0
cdef
EnumB0
eb0
=
EB0
cdef
public
Int1
i1
=
0
cdef
public
EnumA1
ea1
=
EA1
cdef
public
EnumB1
eb1
=
EB1
# --
ctypedef
struct
StructA0
:
int
SA0
ctypedef
public
struct
StructA1
:
int
SA1
cdef
struct
StructB0
:
int
SB0
cdef
public
struct
StructB1
:
int
SB1
cdef
StructA0
sa0
=
{
'SA0'
:
0
}
cdef
StructB0
sb0
=
{
'SB0'
:
2
}
cdef
public
StructA1
sa1
=
{
'SA1'
:
1
}
cdef
public
StructB1
sb1
=
{
'SB1'
:
3
}
# --
ctypedef
class
Foo0
:
pass
ctypedef
public
class
Foo1
[
type
PyFoo1_Type
,
object
PyFoo1_Object
]:
pass
cdef
class
Bar0
:
pass
cdef
public
class
Bar1
[
type
PyBar1_Type
,
object
PyBar1_Object
]:
pass
cdef
Foo0
f0
=
None
cdef
Bar0
b0
=
None
cdef
public
Foo1
f1
=
None
cdef
public
Bar1
b1
=
None
# --
cdef
void
bar0
():
pass
cdef
public
void
bar1
():
pass
cdef
void
*
spam0
(
object
o
)
except
NULL
:
return
NULL
cdef
public
void
*
spam1
(
object
o
)
except
NULL
:
return
NULL
bar0
()
bar1
()
spam0
(
None
)
spam1
(
None
)
# --
tests/compile/publicapi_pxd_mix.pxd
0 → 100644
View file @
0a56c99d
# --
ctypedef
int
Int0
ctypedef
public
int
Int1
ctypedef
api
int
Int2
ctypedef
public
api
int
Int3
ctypedef
enum
EnumA0
:
EA0
ctypedef
public
enum
EnumA1
:
EA1
ctypedef
api
enum
EnumA2
:
EA2
ctypedef
public
api
enum
EnumA3
:
EA3
cdef
enum
EnumB0
:
EB0
=
0
cdef
public
enum
EnumB1
:
EB1
=
1
cdef
api
enum
EnumB2
:
EB2
=
2
cdef
public
api
enum
EnumB3
:
EB3
=
3
# --
ctypedef
struct
StructA0
:
int
SA0
ctypedef
public
struct
StructA1
:
int
SA1
ctypedef
api
struct
StructA2
:
int
SA2
ctypedef
public
api
struct
StructA3
:
int
SA3
cdef
struct
StructB0
:
int
SB0
cdef
public
struct
StructB1
:
int
SB1
cdef
api
struct
StructB2
:
int
SB2
cdef
public
api
struct
StructB3
:
int
SB3
# --
ctypedef
class
Foo0
:
pass
ctypedef
public
class
Foo1
[
type
PyFoo1_Type
,
object
PyFoo1_Object
]:
pass
ctypedef
api
class
Foo2
[
type
PyFoo2_Type
,
object
PyFoo2_Object
]:
pass
ctypedef
public
api
class
Foo3
[
type
PyFoo3_Type
,
object
PyFoo3_Object
]:
pass
cdef
class
Bar0
:
pass
cdef
public
class
Bar1
[
type
PyBar1_Type
,
object
PyBar1_Object
]:
pass
cdef
api
class
Bar2
[
type
PyBar2_Type
,
object
PyBar2_Object
]:
pass
cdef
public
api
class
Bar3
[
type
PyBar3_Type
,
object
PyBar3_Object
]:
pass
# --
cdef
inline
void
bar0
():
pass
cdef
public
void
bar1
()
cdef
api
void
bar2
()
cdef
public
api
void
bar3
()
cdef
inline
void
*
spam0
(
object
o
)
except
NULL
:
return
NULL
cdef
public
void
*
spam1
(
object
o
)
except
NULL
cdef
api
void
*
spam2
(
object
o
)
nogil
except
NULL
cdef
public
api
void
*
spam3
(
object
o
)
except
NULL
with
gil
# --
#cdef public int i1
#cdef api int i2
#cdef public api int i3
# --
tests/compile/publicapi_pxd_mix.pyx
0 → 100644
View file @
0a56c99d
cdef
class
Foo1
:
pass
cdef
class
Foo2
:
pass
cdef
class
Foo3
:
pass
cdef
class
Bar1
:
pass
cdef
class
Bar2
:
pass
cdef
class
Bar3
:
pass
cdef
public
void
bar1
():
pass
cdef
api
void
bar2
():
pass
cdef
public
api
void
bar3
():
pass
cdef
public
void
*
spam1
(
object
o
)
except
NULL
:
return
NULL
cdef
api
void
*
spam2
(
object
o
)
nogil
except
NULL
:
return
NULL
cdef
public
api
void
*
spam3
(
object
o
)
except
NULL
with
gil
:
return
NULL
tests/run/capiimpl.pyx
View file @
0a56c99d
...
@@ -2,8 +2,20 @@ __doc__ = u"""
...
@@ -2,8 +2,20 @@ __doc__ = u"""
>>> import sys
>>> import sys
>>> sys.getrefcount(Foo.__pyx_vtable__)
>>> sys.getrefcount(Foo.__pyx_vtable__)
2
2
>>> sys.getrefcount(__pyx_capi__['
spam
'])
>>> sys.getrefcount(__pyx_capi__['
ten
'])
2
2
>>> sys.getrefcount(__pyx_capi__['pi'])
2
>>> sys.getrefcount(__pyx_capi__['obj'])
2
>>> sys.getrefcount(__pyx_capi__['dct'])
2
>>> sys.getrefcount(__pyx_capi__['one'])
2
>>> sys.getrefcount(__pyx_capi__['two'])
Traceback (most recent call last):
...
KeyError: 'two'
"""
"""
cdef
public
api
class
Foo
[
type
FooType
,
object
FooObject
]:
cdef
public
api
class
Foo
[
type
FooType
,
object
FooObject
]:
...
@@ -12,3 +24,12 @@ cdef public api class Foo [type FooType, object FooObject]:
...
@@ -12,3 +24,12 @@ cdef public api class Foo [type FooType, object FooObject]:
cdef
api
void
spam
():
cdef
api
void
spam
():
pass
pass
cdef
api
int
ten
=
10
cdef
api
double
pi
=
3.14
cdef
api
object
obj
=
object
()
cdef
api
dict
dct
=
{}
cdef
public
api
int
one
=
1
cdef
public
int
two
=
2
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment