summaryrefslogtreecommitdiff
path: root/tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc
diff options
context:
space:
mode:
Diffstat (limited to 'tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc')
-rw-r--r--tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc212
1 files changed, 212 insertions, 0 deletions
diff --git a/tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc b/tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc
new file mode 100644
index 000000000..49bd758b6
--- /dev/null
+++ b/tools/intergen/cppgen/src/cppgen/cpp_interface_code_generator.cc
@@ -0,0 +1,212 @@
+/**
+ * Copyright (c) 2014, Ford Motor Company
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * Redistributions of source code must retain the above copyright notice, this
+ * list of conditions and the following disclaimer.
+ *
+ * Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following
+ * disclaimer in the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * Neither the name of the Ford Motor Company nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "cppgen/cpp_interface_code_generator.h"
+
+#include "cppgen/generator_preferences.h"
+#include "cppgen/handler_interface.h"
+#include "cppgen/message_factory_function.h"
+#include "cppgen/message_interface.h"
+#include "cppgen/module_manager.h"
+#include "model/interface.h"
+#include "model/type_registry.h"
+
+namespace codegen {
+
+CppInterfaceCodeGenerator::CppInterfaceCodeGenerator(
+ const Interface* interface,
+ const TypePreferences* preferences,
+ ModuleManager* module_manager)
+ : interface_(interface),
+ preferences_(preferences),
+ module_manager_(module_manager),
+ declaration_generator_(preferences, module_manager_),
+ definition_generator_(preferences, module_manager_) {
+}
+
+CppInterfaceCodeGenerator::~CppInterfaceCodeGenerator() {
+}
+
+void CppInterfaceCodeGenerator::GenerateCode() {
+ GenerateEnums();
+ GenerateTypedefs();
+ GenerateStructs();
+ bool type_only_interface =
+ interface_->function_id_enum()->constants().empty();
+ if (!type_only_interface) {
+ GenerateFunctions();
+ GenerateResponses();
+ GenerateNotifications();
+ GenerateHandlerInterfaces();
+ GenerateMessageBaseClasses();
+ GenerateMessageFactories();
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateEnums() {
+ const Interface::EnumList& enums = interface_->enums();
+ for (Interface::EnumList::const_iterator i = enums.begin(), end = enums.end();
+ i != end; ++i) {
+ const Enum* e = *i;
+ declaration_generator_.GenerateCodeForEnum(e);
+ definition_generator_.GenerateCodeForEnum(e);
+ }
+
+ const Enum* func_id_enum = interface_->function_id_enum();
+ // Not all interfaces declare functions, avoid empty enum generation
+ if (!func_id_enum->constants().empty()) {
+ declaration_generator_.GenerateCodeForEnum(func_id_enum);
+ definition_generator_.GenerateCodeForEnum(func_id_enum);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateStructs() {
+ const Interface::StructList& structs = interface_->structs();
+ for (Interface::StructList::const_iterator i = structs.begin(), end = structs
+ .end(); i != end; ++i) {
+ const Struct* s = *i;
+ declaration_generator_.GenerateCodeForStruct(s);
+ definition_generator_.GenerateCodeForStruct(s);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateTypedefs() {
+ const Interface::TypedefList& typedefs = interface_->typedefs();
+ for (Interface::TypedefList::const_iterator i = typedefs.begin(), end =
+ typedefs.end(); i != end; ++i) {
+ const Typedef* tdef = *i;
+ declaration_generator_.GenerateCodeForTypedef(tdef);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateFunctions() {
+ const Interface::FunctionsList& functions = interface_->functions();
+ for (Interface::FunctionsList::const_iterator i = functions.begin(), end =
+ functions.end(); i != end; ++i) {
+ const Function& function = *i;
+ declaration_generator_.GenerateCodeForFunction(function);
+ definition_generator_.GenerateCodeForFunction(function);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateResponses() {
+ const Interface::ResponseList& responses = interface_->generic_responses();
+ for (Interface::ResponseList::const_iterator i = responses.begin(), end =
+ responses.end(); i != end; ++i) {
+ const Response& response = **i;
+ declaration_generator_.GenerateCodeForResponse(response);
+ definition_generator_.GenerateCodeForResponse(response);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateNotifications() {
+ const Interface::NotificationList& notifications =
+ interface_->notifications();
+ for (Interface::NotificationList::const_iterator i = notifications.begin(),
+ end = notifications.end(); i != end; ++i) {
+ const Notification& notification = **i;
+ declaration_generator_.GenerateCodeForNotification(notification);
+ definition_generator_.GenerateCodeForNotification(notification);
+ }
+}
+
+void CppInterfaceCodeGenerator::GenerateHandlerInterfaces() {
+ CppFile& handler_header = module_manager_->HeaderForInterface();
+ CppFile& handler_source = module_manager_->SourceForInterface();
+ HandlerInterface notif_handler(
+ FunctionMessage::kNotification, interface_, &handler_header);
+ notif_handler.Declare(&handler_header.notifications_ns().os());
+ notif_handler.Define(&handler_source.notifications_ns().os());
+
+ HandlerInterface req_handler(
+ FunctionMessage::kRequest, interface_, &handler_header);
+ req_handler.Declare(&handler_header.requests_ns().os());
+ req_handler.Define(&handler_source.requests_ns().os());
+
+ HandlerInterface resp_handler(
+ FunctionMessage::kResponse, interface_, &handler_header);
+ resp_handler.Declare(&handler_header.responses_ns().os());
+ resp_handler.Define(&handler_source.responses_ns().os());
+}
+
+void CppInterfaceCodeGenerator::GenerateMessageBaseClasses() {
+ CppFile& message_base_header = module_manager_->HeaderForInterface();
+ CppFile& message_base_source = module_manager_->SourceForInterface();
+ MessageInterface notif_message(interface_, FunctionMessage::kNotification);
+ notif_message.Declare(&message_base_header.notifications_ns().os());
+ notif_message.Define(&message_base_source.notifications_ns().os());
+
+ MessageInterface request_message(interface_, FunctionMessage::kRequest);
+ request_message.Declare(&message_base_header.requests_ns().os());
+ request_message.Define(&message_base_source.requests_ns().os());
+
+ MessageInterface response_message(interface_, FunctionMessage::kResponse);
+ response_message.Declare(&message_base_header.responses_ns().os());
+ response_message.Define(&message_base_source.responses_ns().os());
+}
+
+void CppInterfaceCodeGenerator::GenerateMessageFactories() {
+ CppFile& factories_header = module_manager_->HeaderForInterface();
+ CppFile& factories_source = module_manager_->SourceForInterface();
+
+ MessageFactoryFunction::SerializationType ser_types[2];
+ size_t ser_types_count = 0;
+ if (preferences_->generate_json) {
+ ser_types[ser_types_count++] = MessageFactoryFunction::kJson;
+ }
+ if (preferences_->generate_dbus) {
+ ser_types[ser_types_count++] = MessageFactoryFunction::kDbus;
+ }
+
+ for (size_t i = 0; i < ser_types_count; ++i) {
+ MessageFactoryFunction request_factory(interface_,
+ ser_types[i],
+ FunctionMessage::kRequest);
+ request_factory.Declare(&factories_header.requests_ns().os(), true);
+ request_factory.Define(&factories_source.requests_ns().os(), true);
+ MessageFactoryFunction response_factory(interface_,
+ ser_types[i],
+ FunctionMessage::kResponse);
+ response_factory.Declare(&factories_header.responses_ns().os(), true);
+ response_factory.Define(&factories_source.responses_ns().os(), true);
+ MessageFactoryFunction notification_factory(
+ interface_,
+ ser_types[i],
+ FunctionMessage::kNotification);
+ notification_factory.Declare(&factories_header.notifications_ns().os(),
+ true);
+ notification_factory.Define(&factories_source.notifications_ns().os(), true);
+ }
+
+}
+
+} // namespace codegen