@@ -82,9 +82,11 @@ def compile_modules_to_c(result: BuildResult, module_names: List[str],
82
82
83
83
84
84
def generate_function_declaration (fn : FuncIR , emitter : Emitter ) -> None :
85
- emitter .emit_line ('{};' .format (native_function_header (fn .decl , emitter )))
85
+ emitter .context .declarations [emitter .native_function_name (fn .decl )] = HeaderDeclaration (
86
+ '{};' .format (native_function_header (fn .decl , emitter )))
86
87
if fn .name != TOP_LEVEL_NAME :
87
- emitter .emit_line ('{};' .format (wrapper_function_header (fn , emitter .names )))
88
+ emitter .context .declarations [PREFIX + fn .cname (emitter .names )] = HeaderDeclaration (
89
+ '{};' .format (wrapper_function_header (fn , emitter .names )))
88
90
89
91
90
92
def encode_as_c_string (s : str ) -> Tuple [str , int ]:
@@ -127,6 +129,7 @@ def generate_c_for_modules(self) -> List[Tuple[str, str]]:
127
129
128
130
base_emitter = Emitter (self .context )
129
131
base_emitter .emit_line ('#include "__native.h"' )
132
+ base_emitter .emit_line ('#include "__native_internal.h"' )
130
133
emitter = base_emitter
131
134
132
135
for (_ , literal ), identifier in self .literals .items ():
@@ -140,6 +143,7 @@ def generate_c_for_modules(self) -> List[Tuple[str, str]]:
140
143
if multi_file :
141
144
emitter = Emitter (self .context )
142
145
emitter .emit_line ('#include "__native.h"' )
146
+ emitter .emit_line ('#include "__native_internal.h"' )
143
147
144
148
self .declare_module (module_name , emitter )
145
149
self .declare_internal_globals (module_name , emitter )
@@ -166,6 +170,33 @@ def generate_c_for_modules(self) -> List[Tuple[str, str]]:
166
170
name = ('__native_{}.c' .format (emitter .names .private_name (module_name )))
167
171
file_contents .append ((name , '' .join (emitter .fragments )))
168
172
173
+ # The external header file contains type declarations while
174
+ # the internal contains declarations of functions and objects
175
+ # (which are shared between shared libraries via dynamic
176
+ # linking tables and not accessed directly.)
177
+ ext_declarations = Emitter (self .context )
178
+ ext_declarations .emit_line ('#ifndef MYPYC_NATIVE_H' )
179
+ ext_declarations .emit_line ('#define MYPYC_NATIVE_H' )
180
+ ext_declarations .emit_line ('#include <Python.h>' )
181
+ ext_declarations .emit_line ('#include <CPy.h>' )
182
+
183
+ declarations = Emitter (self .context )
184
+ declarations .emit_line ('#ifndef MYPYC_NATIVE_INTERNAL_H' )
185
+ declarations .emit_line ('#define MYPYC_NATIVE_INTERNAL_H' )
186
+ declarations .emit_line ('#include <Python.h>' )
187
+ declarations .emit_line ('#include <CPy.h>' )
188
+ declarations .emit_line ('#include "__native.h"' )
189
+ declarations .emit_line ()
190
+ declarations .emit_line ('int CPyGlobalsInit(void);' )
191
+ declarations .emit_line ()
192
+
193
+ for module_name , module in self .modules :
194
+ self .declare_finals (module_name , module .final_names , declarations )
195
+ for cl in module .classes :
196
+ generate_class_type_decl (cl , emitter , ext_declarations , declarations )
197
+ for fn in module .functions :
198
+ generate_function_declaration (fn , declarations )
199
+
169
200
sorted_decls = self .toposort_declarations ()
170
201
171
202
emitter = base_emitter
@@ -176,33 +207,25 @@ def generate_c_for_modules(self) -> List[Tuple[str, str]]:
176
207
177
208
emitter .emit_line ()
178
209
179
- declarations = Emitter (self .context )
180
- declarations .emit_line ('#include <Python.h>' )
181
- declarations .emit_line ('#include <CPy.h>' )
182
- declarations .emit_line ()
183
- declarations .emit_line ('int CPyGlobalsInit(void);' )
184
- declarations .emit_line ()
185
-
186
210
for declaration in sorted_decls :
187
- if declaration .needs_extern :
188
- declarations .emit_lines (
211
+ decls = ext_declarations if declaration .is_type else declarations
212
+ if not declaration .is_type :
213
+ decls .emit_lines (
189
214
'extern {}' .format (declaration .decl [0 ]), * declaration .decl [1 :])
190
215
emitter .emit_lines (* declaration .decl )
191
216
else :
192
- declarations .emit_lines (* declaration .decl )
193
-
194
- for module_name , module in self .modules :
195
- self .declare_finals (module_name , module .final_names , declarations )
196
- for cl in module .classes :
197
- generate_class_type_decl (cl , emitter , declarations )
198
- for fn in module .functions :
199
- generate_function_declaration (fn , declarations )
217
+ decls .emit_lines (* declaration .decl )
200
218
201
219
if self .shared_lib_name :
202
220
self .generate_shared_lib_init (emitter )
203
221
222
+ ext_declarations .emit_line ('#endif' )
223
+ declarations .emit_line ('#endif' )
224
+
204
225
return file_contents + [('__native.c' , '' .join (emitter .fragments )),
205
- ('__native.h' , '' .join (declarations .fragments ))]
226
+ ('__native_internal.h' , '' .join (declarations .fragments )),
227
+ ('__native.h' , '' .join (ext_declarations .fragments )),
228
+ ]
206
229
207
230
def generate_shared_lib_init (self , emitter : Emitter ) -> None :
208
231
"""Generate the init function for a shared library.
@@ -438,17 +461,16 @@ def _toposort_visit(name: str) -> None:
438
461
return result
439
462
440
463
def declare_global (self , type_spaced : str , name : str ,
464
+ * ,
441
465
initializer : Optional [str ] = None ) -> None :
442
466
if not initializer :
443
467
defn = None
444
468
else :
445
469
defn = ['{}{} = {};' .format (type_spaced , name , initializer )]
446
470
if name not in self .context .declarations :
447
471
self .context .declarations [name ] = HeaderDeclaration (
448
- set (),
449
- ['{}{};' .format (type_spaced , name )],
450
- defn ,
451
- needs_extern = True ,
472
+ '{}{};' .format (type_spaced , name ),
473
+ defn = defn ,
452
474
)
453
475
454
476
def declare_internal_globals (self , module_name : str , emitter : Emitter ) -> None :
0 commit comments