1 /* 2 * Copyright (C) 2019 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #pragma once 18 19 #include <map> 20 #include <set> 21 #include <string> 22 #include <vector> 23 #include "Reference.h" 24 25 namespace android { 26 27 struct CompoundType; 28 struct Coordinator; 29 struct Formatter; 30 struct FQName; 31 struct Interface; 32 struct Method; 33 struct NamedType; 34 struct Scope; 35 struct Type; 36 37 struct FieldWithVersion { 38 const NamedReference<Type>* field; 39 // name of the field appended by the 40 std::string fullName; 41 std::pair<size_t, size_t> version; 42 }; 43 44 struct ProcessedCompoundType { 45 // map modified name to field. This modified name is old.new 46 std::vector<FieldWithVersion> fields; 47 std::set<const NamedType*> subTypes; 48 }; 49 50 struct ReplacedTypeInfo { 51 // if a HIDL type is replaced, this returns the new AIDL type 52 // android.hardware.safe_enum@1.0::Monostate -> boolean 53 std::string aidlReplacedType; 54 // if a HIDL type is replaced, this is the FQName of the new AIDL type 55 // android.hardware.safe_enum@1.0::Monostate -> std::nullopt 56 std::optional<std::string> aidlReplacedFQName; 57 // if a HIDL type is replaced, this returns the function needed to generate translation 58 std::optional<std::function<void(Formatter&)>> translateField; 59 }; 60 61 enum class AidlBackend { UNKNOWN, NDK, CPP, JAVA }; 62 63 struct AidlHelper { 64 /* FQName helpers */ 65 // getAidlName returns the type names 66 // backend == UNKNOWN 67 // android.hardware.foo@1.0::IBar::Baz -> Baz 68 // backend == CPP || backend == NDK 69 // android.hardware.foo@1.0::IBar::Baz -> IBar::Baz 70 // backend == JAVA 71 // android.hardware.foo@1.0::IBar::Baz -> IBar.Baz 72 static std::string getAidlName(const FQName& fqName, 73 AidlBackend backend = AidlBackend::UNKNOWN); 74 75 // getAidlPackage returns the AIDL package 76 // android.hardware.foo@1.x -> android.hardware.foo 77 // android.hardware.foo@2.x -> android.hardware.foo2 78 static std::string getAidlPackage(const FQName& fqName); 79 // returns getAidlPackage(fqName) with '.' replaced by '/' 80 // android.hardware.foo@1.x -> android/hardware/foo 81 static std::string getAidlPackagePath(const FQName& fqName); 82 83 // getAidlFQName = getAidlPackage + "." + getAidlName 84 static std::optional<std::string> getAidlFQName(const FQName& fqName); 85 86 // if a HIDL type is replaced, this returns the ReplacedTypeInfo for the new AIDL type 87 static std::optional<const ReplacedTypeInfo> getAidlReplacedType(const FQName& fqName); 88 89 static void emitFileHeader( 90 Formatter& out, const NamedType& type, 91 const std::map<const NamedType*, const ProcessedCompoundType>& processedTypes); 92 static Formatter getFileWithHeader( 93 const NamedType& namedType, const Coordinator& coordinator, 94 const std::map<const NamedType*, const ProcessedCompoundType>& processedTypes); 95 96 /* Methods for Type */ 97 static std::string getAidlType(const Type& type, const FQName& relativeTo, 98 AidlBackend backend = AidlBackend::UNKNOWN); 99 100 /* Methods for NamedType */ 101 static void emitAidl( 102 const NamedType& namedType, Formatter& out, 103 const std::map<const NamedType*, const ProcessedCompoundType>& processedTypes); 104 105 // Walk through all of the type's parents until we reach the top and return. 106 static const NamedType* getTopLevelType(const NamedType* type); 107 108 /* Methods for Interface */ 109 static void emitAidl(const Interface& interface, Formatter& out, 110 const std::map<const NamedType*, const ProcessedCompoundType>&); 111 // Returns all methods that would exist in an AIDL equivalent interface 112 static std::vector<const Method*> getUserDefinedMethods(Formatter& out, 113 const Interface& interface); 114 115 static void processCompoundType(const CompoundType& compoundType, 116 ProcessedCompoundType* processedType, 117 const std::string& fieldNamePrefix); 118 119 static Formatter& notes(); 120 static void setNotes(Formatter* formatter); 121 122 // return the full file names for the header/source files based on the backend 123 static std::string translateHeaderFile(const FQName& fqName, AidlBackend backend); 124 static std::string translateSourceFile(const FQName& fqName, AidlBackend backend); 125 126 static void emitTranslation( 127 const Coordinator& coordinator, const FQName& fqName, 128 const std::set<const NamedType*>& namedTypesInPackage, 129 const std::map<const NamedType*, const ProcessedCompoundType>& processedTypes); 130 static void setFileHeader(const std::string& file); 131 static void emitFileHeader(Formatter& out); setExpandExtendedAidlHelper132 static void setExpandExtended(bool expand) { expandExtended = expand; }; isExpandExtendedAidlHelper133 static bool isExpandExtended() { return expandExtended; }; 134 static bool shouldBeExpanded(const FQName& source, const FQName& extended); 135 136 private: 137 // This is the formatter to use for additional conversion output 138 static Formatter* notesFormatter; 139 static std::string fileHeader; 140 static bool expandExtended; 141 }; 142 143 } // namespace android 144