forked from wegamekinglc/alglib
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgenerate_symbols.py
91 lines (71 loc) · 3.09 KB
/
generate_symbols.py
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
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
""" Symbol management to generate .def file. """
import glob
import os
import six
import subprocess
from distutils import msvc9compiler
from platform import architecture
VC_VERSION = 14 # msvc9compiler.VERSION
ARCH = "x64" if architecture()[0] == "64bit" else "x86"
def symbol_generator_from_obj_file(object_file):
command = ['nm', '--extern-only', '--defined-only', object_file]
# don't show a window when executing the subprocess
startupinfo = subprocess.STARTUPINFO()
startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
nm_result = subprocess.check_output(command, startupinfo=startupinfo)
def _is_ql_symbols(symb):
# Includes all the symbols containing QuantLib except the ones with
# AVError and all the scalar deleting destructor (prefixed with _G)
# and all the vector deleting destructor (prefixed with a _E)
# and ?AVError (not yet sure what cause the problem :
# (Error 1 error LNK2001: unresolved external symbol
# "??_R0?AVError@QuantLib@@@8??0Error@QuantLib@@QAE@ABV01@@Z20"
# (??_R0?AVError@QuantLib@@@8??0Error@QuantLib@@QAE@ABV01@@Z20)
# QuantLib.exp QuantLib
# )
# See http://en.wikipedia.org/wiki/Visual_C%2B%2B_name_mangling for
# reference
return (
'adept' in symb and
'?AV' not in symb and
#'?AVap_error' not in symb and
#'?AW4ae_error' not in symb and
'??_G' not in symb and
'??_E' not in symb
)
def _is_boost_assertion(symb):
return '?assertion_failed@boost' in mangled_symbol
for line in six.text_type(nm_result, 'ascii').split('\n'):
# Example line:
# 0000000000000000 R ?value@?$integral_constant@_N$00@tr1@std@@2_NB
# Find the symbol location in the line
idx = line.find('?')
# Get the symbol type
stat = line[idx-2:idx].strip()
if stat == 'w': # skip weak symbols
continue
mangled_symbol = line[idx:].strip()
if len(mangled_symbol) > 0:
if _is_ql_symbols(mangled_symbol) or _is_boost_assertion(mangled_symbol):
yield mangled_symbol
def process_directory(directory_name):
for object_file in glob.glob(os.path.join(directory_name, '*.obj')):
for symbol in symbol_generator_from_obj_file(object_file):
yield symbol
LIBRARY_NAME = "adept"
HEADER = """LIBRARY "%s"
EXPORTS
""" % LIBRARY_NAME
def generate_deffile_from_dir(input_directory, output_file):
with open(output_file, 'w') as fh:
fh.write(HEADER)
for symbol in process_directory(input_directory):
fh.write(' {}\n'.format(symbol))
def main():
input_directory = r"D:\dev\alglib\build\Adept\adept.dir\Release"
symbols_file = "adept_symbols.def"
output_file = os.path.abspath(os.path.join(os.path.dirname(__file__), symbols_file))
generate_deffile_from_dir(input_directory, output_file)
print ('{} generated'.format(output_file))
if __name__ == '__main__':
main()