OLD | NEW |
1 /* | 1 /* |
2 * This file is part of Adblock Plus <https://adblockplus.org/>, | 2 * This file is part of Adblock Plus <https://adblockplus.org/>, |
3 * Copyright (C) 2006-2017 eyeo GmbH | 3 * Copyright (C) 2006-2017 eyeo GmbH |
4 * | 4 * |
5 * Adblock Plus is free software: you can redistribute it and/or modify | 5 * Adblock Plus is free software: you can redistribute it and/or modify |
6 * it under the terms of the GNU General Public License version 3 as | 6 * it under the terms of the GNU General Public License version 3 as |
7 * published by the Free Software Foundation. | 7 * published by the Free Software Foundation. |
8 * | 8 * |
9 * Adblock Plus is distributed in the hope that it will be useful, | 9 * Adblock Plus is distributed in the hope that it will be useful, |
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of | 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
12 * GNU General Public License for more details. | 12 * GNU General Public License for more details. |
13 * | 13 * |
14 * You should have received a copy of the GNU General Public License | 14 * You should have received a copy of the GNU General Public License |
15 * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>. | 15 * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>. |
16 */ | 16 */ |
17 | 17 |
18 #include <cstdio> | 18 #include <cstdio> |
19 | 19 |
20 #include <emscripten.h> | |
21 | |
22 #include "generator.h" | 20 #include "generator.h" |
| 21 #include "library.h" |
23 | 22 |
24 namespace | 23 namespace |
25 { | 24 { |
26 std::vector<bindings_internal::ClassInfo> classes; | 25 std::vector<bindings_internal::ClassInfo> classes; |
27 std::vector<bindings_internal::NamespaceInfo> namespaces; | 26 std::vector<bindings_internal::NamespaceInfo> namespaces; |
28 | 27 |
29 void printProperties(const bindings_internal::PropertyList& properties) | 28 void printProperties(const bindings_internal::PropertyList& properties) |
30 { | 29 { |
31 for (const auto& property : properties) | 30 for (const auto& property : properties) |
32 { | 31 { |
(...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
134 break; | 133 break; |
135 case TypeCategory::DOUBLE: | 134 case TypeCategory::DOUBLE: |
136 signature += 'd'; | 135 signature += 'd'; |
137 break; | 136 break; |
138 default: | 137 default: |
139 throw std::runtime_error("Unexpected function argument type"); | 138 throw std::runtime_error("Unexpected function argument type"); |
140 } | 139 } |
141 args.push_back(type); | 140 args.push_back(type); |
142 } | 141 } |
143 | 142 |
144 get_function_name(function, signature.c_str()); | 143 GetFunctionName(name, function, signature.c_str()); |
145 } | 144 } |
146 | 145 |
147 bool FunctionInfo::empty() const | 146 bool FunctionInfo::empty() const |
148 { | 147 { |
149 return name[0] == '\0'; | 148 return name[0] == '\0'; |
150 } | 149 } |
151 | 150 |
152 void FunctionInfo::get_function_name(void* ptr, const char* signature) | |
153 { | |
154 // This is a hack, C++ won't let us get the mangled function name. | |
155 // JavaScript is more dynamic so we pass the pointer to our function | |
156 // there. With that and the function signature we can call the function - | |
157 // with a full stack so that we will cause it to abort. Sometimes the | |
158 // function we are calling will also be missing from the build. The result | |
159 // is the same: abort() is called which in turn calls stackTrace(). By | |
160 // replacing stackTrace() we get access to the call stack and search it | |
161 // for the name of our function. | |
162 | |
163 EM_ASM_ARGS({ | |
164 var signature = AsciiToString($2); | |
165 var args = []; | |
166 for (var i = 1; i < signature.length; i++) | |
167 args.push(0); | |
168 | |
169 var oldPrint = Module.print; | |
170 var oldPrintErr = Module.printErr; | |
171 var oldStackTrace = stackTrace; | |
172 var sp = Runtime.stackSave(); | |
173 Module.print = function(){}; | |
174 Module.printErr = function(){}; | |
175 stackTrace = function() | |
176 { | |
177 var stack = []; | |
178 for (var f = arguments.callee.caller; f; f = f.caller) | |
179 { | |
180 if (f.name) | |
181 { | |
182 if (f.name.indexOf("dynCall") == 0) | |
183 break; | |
184 else | |
185 stack.push(f.name); | |
186 } | |
187 } | |
188 | |
189 result = stack[stack.length - 1]; | |
190 if (result && result.indexOf("__wrapper") >= 0) | |
191 result = stack[stack.length - 2]; | |
192 throw result; | |
193 }; | |
194 | |
195 Runtime.stackRestore(STACK_MAX); | |
196 | |
197 try | |
198 { | |
199 Runtime.dynCall(signature, HEAP32[$1 >> 2], args); | |
200 } | |
201 catch(e) | |
202 { | |
203 Module.stringToAscii(e, $0); | |
204 } | |
205 finally | |
206 { | |
207 Runtime.stackRestore(sp); | |
208 Module.print = oldPrint; | |
209 Module.printErr = oldPrintErr; | |
210 stackTrace = oldStackTrace; | |
211 } | |
212 }, name, ptr, signature); | |
213 } | |
214 | |
215 ClassInfo* find_class(TYPEID classID) | 151 ClassInfo* find_class(TYPEID classID) |
216 { | 152 { |
217 for (auto& classInfo : classes) | 153 for (auto& classInfo : classes) |
218 if (classInfo.id == classID) | 154 if (classInfo.id == classID) |
219 return &classInfo; | 155 return &classInfo; |
220 return nullptr; | 156 return nullptr; |
221 } | 157 } |
222 | 158 |
223 void register_class(const char* name, TYPEID classID, TYPEID baseClassID, | 159 void register_class(const char* name, TYPEID classID, TYPEID baseClassID, |
224 ptrdiff_t ref_counted_offset) | 160 ptrdiff_t ref_counted_offset) |
(...skipping 339 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
564 | 500 |
565 void printBindings() | 501 void printBindings() |
566 { | 502 { |
567 bindings_internal::printHelpers(); | 503 bindings_internal::printHelpers(); |
568 | 504 |
569 for (const auto& item : classes) | 505 for (const auto& item : classes) |
570 bindings_internal::printClass(item); | 506 bindings_internal::printClass(item); |
571 for (const auto& item : namespaces) | 507 for (const auto& item : namespaces) |
572 bindings_internal::printNamespace(item); | 508 bindings_internal::printNamespace(item); |
573 } | 509 } |
OLD | NEW |