| 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 "generator.h" | 20 #include "generator.h" | 
| 21 #include "library.h" | 21 #include "library.h" | 
| 22 | 22 | 
| 23 namespace | 23 namespace | 
| 24 { | 24 { | 
| 25   std::vector<bindings_internal::ClassInfo> classes; | 25   std::vector<bindings_internal::ClassInfo> classes; | 
|  | 26   std::vector<bindings_internal::NamespaceInfo> namespaces; | 
|  | 27 | 
|  | 28   void printProperties(const bindings_internal::Properties& properties) | 
|  | 29   { | 
|  | 30     for (const auto& property : properties) | 
|  | 31     { | 
|  | 32       if (property.jsValue.empty()) | 
|  | 33       { | 
|  | 34         printf("get %s%s,\n", property.name.c_str(), | 
|  | 35                wrapCall(property.getter, false).c_str()); | 
|  | 36         if (!property.setter.empty()) | 
|  | 37         { | 
|  | 38           printf("set %s%s,\n", property.name.c_str(), | 
|  | 39                  wrapCall(property.setter, false).c_str()); | 
|  | 40         } | 
|  | 41       } | 
|  | 42       else | 
|  | 43         printf("%s: %s,\n", property.name.c_str(), property.jsValue.c_str()); | 
|  | 44     } | 
|  | 45   } | 
|  | 46 | 
|  | 47   void printMethods(const bindings_internal::Methods& methods, | 
|  | 48                     bool instanceOnly = true) | 
|  | 49   { | 
|  | 50     for (const auto& method : methods) | 
|  | 51       if (!instanceOnly || method.call.instance_function) | 
|  | 52         printf("%s: %s,\n", method.name.c_str(), wrapCall(method.call).c_str()); | 
|  | 53   } | 
| 26 } | 54 } | 
| 27 | 55 | 
| 28 namespace bindings_internal | 56 namespace bindings_internal | 
| 29 { | 57 { | 
| 30   FunctionInfo::FunctionInfo() | 58   FunctionInfo::FunctionInfo() | 
| 31   { | 59   { | 
| 32   } | 60   } | 
| 33 | 61 | 
| 34   FunctionInfo::FunctionInfo(TypeCategory returnType, TYPEID pointerType, | 62   FunctionInfo::FunctionInfo(TypeCategory returnType, TYPEID pointerType, | 
| 35       std::initializer_list<TypeCategory> argTypes, bool instance_function, | 63       std::initializer_list<TypeCategory> argTypes, bool instance_function, | 
| (...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 183 | 211 | 
| 184     if (classInfo->subclass_differentiator.offset != SIZE_MAX) | 212     if (classInfo->subclass_differentiator.offset != SIZE_MAX) | 
| 185       throw std::runtime_error("More than one subclass differentiator defined fo
     r class " + classInfo->name); | 213       throw std::runtime_error("More than one subclass differentiator defined fo
     r class " + classInfo->name); | 
| 186 | 214 | 
| 187     DifferentiatorInfo differentiatorInfo; | 215     DifferentiatorInfo differentiatorInfo; | 
| 188     differentiatorInfo.offset = offset; | 216     differentiatorInfo.offset = offset; | 
| 189     differentiatorInfo.mapping = mapping; | 217     differentiatorInfo.mapping = mapping; | 
| 190     classInfo->subclass_differentiator = differentiatorInfo; | 218     classInfo->subclass_differentiator = differentiatorInfo; | 
| 191   } | 219   } | 
| 192 | 220 | 
|  | 221   NamespaceInfo* find_namespace(const char* namespaceName) | 
|  | 222   { | 
|  | 223     for (auto& namespaceInfo : namespaces) | 
|  | 224       if (namespaceInfo.name == namespaceName) | 
|  | 225         return &namespaceInfo; | 
|  | 226     return nullptr; | 
|  | 227   } | 
|  | 228 | 
|  | 229   void register_namespace(const char* name) | 
|  | 230   { | 
|  | 231     if (find_namespace(name)) | 
|  | 232       throw std::runtime_error(std::string("Duplicate definition for namespace "
     ) + name); | 
|  | 233 | 
|  | 234     NamespaceInfo namespaceInfo; | 
|  | 235     namespaceInfo.name = name; | 
|  | 236     namespaces.push_back(namespaceInfo); | 
|  | 237   } | 
|  | 238 | 
|  | 239   void register_namespace_property(const char* namespaceName, const char* name, | 
|  | 240       const FunctionInfo& getter, const FunctionInfo& setter) | 
|  | 241   { | 
|  | 242     NamespaceInfo* namespaceInfo = find_namespace(namespaceName); | 
|  | 243     if (!namespaceInfo) | 
|  | 244       throw std::runtime_error(std::string("Property defined on unknown namespac
     e: ") + name); | 
|  | 245 | 
|  | 246     PropertyInfo propertyInfo; | 
|  | 247     propertyInfo.name = name; | 
|  | 248     propertyInfo.getter = getter; | 
|  | 249     propertyInfo.setter = setter; | 
|  | 250     namespaceInfo->properties.push_back(propertyInfo); | 
|  | 251   } | 
|  | 252 | 
|  | 253   void register_namespace_method(const char* namespaceName, const char* name, | 
|  | 254       const FunctionInfo& call) | 
|  | 255   { | 
|  | 256     NamespaceInfo* namespaceInfo = find_namespace(namespaceName); | 
|  | 257     if (!namespaceInfo) | 
|  | 258       throw std::runtime_error(std::string("Method defined on unknown namespace:
      ") + name); | 
|  | 259 | 
|  | 260     MethodInfo methodInfo; | 
|  | 261     methodInfo.name = name; | 
|  | 262     methodInfo.call = call; | 
|  | 263     namespaceInfo->methods.push_back(methodInfo); | 
|  | 264   } | 
|  | 265 | 
| 193   std::string generateCall(const FunctionInfo& call, | 266   std::string generateCall(const FunctionInfo& call, | 
| 194       std::vector<std::string>& params) | 267       std::vector<std::string>& params) | 
| 195   { | 268   { | 
| 196     if (call.returnType == TypeCategory::DEPENDENT_STRING || | 269     if (call.returnType == TypeCategory::DEPENDENT_STRING || | 
| 197         call.returnType == TypeCategory::OWNED_STRING) | 270         call.returnType == TypeCategory::OWNED_STRING) | 
| 198     { | 271     { | 
| 199       params.insert(params.begin(), "string"); | 272       params.insert(params.begin(), "string"); | 
| 200     } | 273     } | 
| 201 | 274 | 
| 202     std::string call_str(call.name); | 275     std::string call_str(call.name); | 
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 276       if (i > 0) | 349       if (i > 0) | 
| 277         prefix += ", "; | 350         prefix += ", "; | 
| 278       prefix += argName; | 351       prefix += argName; | 
| 279 | 352 | 
| 280       if (call.args[i] == TypeCategory::STRING_REF) | 353       if (call.args[i] == TypeCategory::STRING_REF) | 
| 281       { | 354       { | 
| 282         hasStringArgs = true; | 355         hasStringArgs = true; | 
| 283         params.push_back(std::string("createString(") + argName + ")"); | 356         params.push_back(std::string("createString(") + argName + ")"); | 
| 284       } | 357       } | 
| 285       else if (call.args[i] == TypeCategory::CLASS_PTR) | 358       else if (call.args[i] == TypeCategory::CLASS_PTR) | 
| 286         params.push_back(argName + "._pointer"); | 359         params.push_back(argName + " ? " + argName + "._pointer : 0"); | 
| 287       else if (call.args[i] == TypeCategory::INT64) | 360       else if (call.args[i] == TypeCategory::INT64) | 
| 288       { | 361       { | 
| 289         // 64-bit integers are passed as two integer parameters | 362         // 64-bit integers are passed as two integer parameters | 
| 290         params.push_back(argName + " >>> 0"); | 363         params.push_back(argName + " >>> 0"); | 
| 291         params.push_back(argName + " / 0x100000000 >>> 0"); | 364         params.push_back(argName + " / 0x100000000 >>> 0"); | 
| 292       } | 365       } | 
| 293       else | 366       else | 
| 294         params.push_back(argName); | 367         params.push_back(argName); | 
| 295     } | 368     } | 
| 296     prefix += ")\n{\n"; | 369     prefix += ")\n{\n"; | 
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 360           Module._ReleaseRef(this._pointer + ref_counted_offset); | 433           Module._ReleaseRef(this._pointer + ref_counted_offset); | 
| 361         }; | 434         }; | 
| 362         return result; | 435         return result; | 
| 363       } | 436       } | 
| 364     )"); | 437     )"); | 
| 365   } | 438   } | 
| 366 | 439 | 
| 367   void printClass(const ClassInfo& cls) | 440   void printClass(const ClassInfo& cls) | 
| 368   { | 441   { | 
| 369     // Begin class definition | 442     // Begin class definition | 
| 370 |  | 
| 371     ClassInfo* baseClass = find_class(cls.baseClass); | 443     ClassInfo* baseClass = find_class(cls.baseClass); | 
| 372     printf("exports.%s = createClass(%s, %i, {\n", cls.name.c_str(), | 444     printf("exports.%s = createClass(%s, %i, {\n", cls.name.c_str(), | 
| 373         (baseClass ? ("exports." + baseClass->name).c_str() : "null"), | 445         (baseClass ? ("exports." + baseClass->name).c_str() : "null"), | 
| 374         cls.ref_counted_offset); | 446         cls.ref_counted_offset); | 
| 375 | 447 | 
| 376     // Print prototype members | 448     // Print prototype members | 
| 377 | 449     printProperties(cls.properties); | 
| 378     for (const auto& property : cls.properties) | 450     printMethods(cls.methods); | 
| 379     { |  | 
| 380       if (property.jsValue.empty()) |  | 
| 381       { |  | 
| 382         printf("get %s%s,\n", property.name.c_str(), |  | 
| 383                wrapCall(property.getter, false).c_str()); |  | 
| 384         if (!property.setter.empty()) |  | 
| 385         { |  | 
| 386           printf("set %s%s,\n", property.name.c_str(), |  | 
| 387                  wrapCall(property.setter, false).c_str()); |  | 
| 388         } |  | 
| 389       } |  | 
| 390       else |  | 
| 391         printf("%s: %s,\n", property.name.c_str(), property.jsValue.c_str()); |  | 
| 392     } |  | 
| 393 |  | 
| 394     for (const auto& method : cls.methods) |  | 
| 395       if (method.call.instance_function) |  | 
| 396         printf("%s: %s,\n", method.name.c_str(), wrapCall(method.call).c_str()); |  | 
| 397 | 451 | 
| 398     // End class definition | 452     // End class definition | 
| 399 |  | 
| 400     printf("});\n"); | 453     printf("});\n"); | 
| 401 | 454 | 
| 402     // Print static members | 455     // Print static members | 
| 403 |  | 
| 404     DifferentiatorInfo differentiator = cls.subclass_differentiator; | 456     DifferentiatorInfo differentiator = cls.subclass_differentiator; | 
| 405     if (differentiator.offset != SIZE_MAX) | 457     if (differentiator.offset != SIZE_MAX) | 
| 406     { | 458     { | 
| 407       printf("var %s_mapping = \n", cls.name.c_str()); | 459       printf("var %s_mapping = \n", cls.name.c_str()); | 
| 408       puts("{"); | 460       puts("{"); | 
| 409       for (const auto& item : differentiator.mapping) | 461       for (const auto& item : differentiator.mapping) | 
| 410         printf("  %i: '%s',\n", item.first, item.second.c_str()); | 462         printf("  %i: '%s',\n", item.first, item.second.c_str()); | 
| 411       puts("};"); | 463       puts("};"); | 
| 412 | 464 | 
| 413       printf("exports.%s.fromPointer = function(ptr)\n", cls.name.c_str()); | 465       printf("exports.%s.fromPointer = function(ptr)\n", cls.name.c_str()); | 
| (...skipping 14 matching lines...) Expand all  Loading... | 
| 428 | 480 | 
| 429     for (const auto& method : cls.methods) | 481     for (const auto& method : cls.methods) | 
| 430     { | 482     { | 
| 431       if (!method.call.instance_function) | 483       if (!method.call.instance_function) | 
| 432       { | 484       { | 
| 433         printf("exports.%s.%s = %s;\n", cls.name.c_str(), method.name.c_str(), | 485         printf("exports.%s.%s = %s;\n", cls.name.c_str(), method.name.c_str(), | 
| 434                wrapCall(method.call).c_str()); | 486                wrapCall(method.call).c_str()); | 
| 435       } | 487       } | 
| 436     } | 488     } | 
| 437   } | 489   } | 
|  | 490 | 
|  | 491   void printNamespace(const NamespaceInfo& namespaceInfo) | 
|  | 492   { | 
|  | 493     printf("exports.%s = {\n", namespaceInfo.name.c_str()); | 
|  | 494     printProperties(namespaceInfo.properties); | 
|  | 495     printMethods(namespaceInfo.methods, false); | 
|  | 496     puts("};"); | 
|  | 497   } | 
| 438 } | 498 } | 
| 439 | 499 | 
| 440 void printBindings() | 500 void printBindings() | 
| 441 { | 501 { | 
| 442   bindings_internal::printHelpers(); | 502   bindings_internal::printHelpers(); | 
| 443 | 503 | 
| 444   for (const auto& item : classes) | 504   for (const auto& item : classes) | 
| 445     bindings_internal::printClass(item); | 505     bindings_internal::printClass(item); | 
|  | 506   for (const auto& item : namespaces) | 
|  | 507     bindings_internal::printNamespace(item); | 
| 446 } | 508 } | 
| OLD | NEW | 
|---|