1 /* 2 * Copyright (C) 2016 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 #ifndef COORDINATOR_H_ 18 19 #define COORDINATOR_H_ 20 21 #include <android-base/macros.h> 22 #include <hidl-util/FQName.h> 23 #include <hidl-util/Formatter.h> 24 #include <utils/Errors.h> 25 #include <map> 26 #include <set> 27 #include <string> 28 #include <vector> 29 30 namespace android { 31 32 struct AST; 33 struct Type; 34 35 struct Coordinator { CoordinatorCoordinator36 Coordinator() {}; 37 38 const std::string& getRootPath() const; 39 void setRootPath(const std::string &rootPath); 40 void setOutputPath(const std::string& outputPath); 41 42 void setVerbose(bool value); 43 bool isVerbose() const; 44 45 void setDepFile(const std::string& depFile); 46 47 const std::string& getOwner() const; 48 void setOwner(const std::string& owner); 49 50 // adds path only if it doesn't exist 51 status_t addPackagePath(const std::string& root, const std::string& path, std::string* error); 52 // adds path if it hasn't already been added 53 void addDefaultPackagePath(const std::string& root, const std::string& path); 54 55 enum class Location { 56 STANDARD_OUT, 57 DIRECT, // mOutputPath + file name 58 PACKAGE_ROOT, // e.x. mRootPath + /nfc/1.0/Android.bp 59 GEN_OUTPUT, // e.x. mOutputPath + /android/hardware/foo/1.0/*.cpp 60 GEN_SANITIZED, // e.x. mOutputPath + /android/hardware/foo/V1_0/*.cpp 61 }; 62 63 status_t getFilepath(const FQName& fqName, Location location, const std::string& fileName, 64 std::string* path) const; 65 66 Formatter getFormatter(const FQName& fqName, Location location, 67 const std::string& fileName) const; 68 69 // must be called before file access 70 void onFileAccess(const std::string& path, const std::string& mode) const; 71 72 status_t writeDepFile(const std::string& forFile) const; 73 74 enum class Enforce { 75 FULL, // default 76 NO_HASH, // only for use with -Lhash 77 NONE, // only for use during enforcement 78 }; 79 80 // Attempts to parse the interface/types referred to by fqName. 81 // Parsing an interface also parses the associated package's types.hal 82 // file if it exists. 83 // If "parsedASTs" is non-NULL, successfully parsed ASTs are inserted 84 // into the set. 85 // If !enforce, enforceRestrictionsOnPackage won't be run. 86 AST* parse(const FQName& fqName, std::set<AST*>* parsedASTs = nullptr, 87 Enforce enforcement = Enforce::FULL) const; 88 89 // Same as parse, but it distinguishes between "missing file" and "could not parse AST" 90 // return OK, out *ast: 91 // 0xdeadbeef -> successfully parsed 92 // nullptr -> file not present 93 // return !OK 94 // could not parse AST and file exists 95 status_t parseOptional(const FQName& fqName, AST** ast, std::set<AST*>* parsedASTs = nullptr, 96 Enforce enforcement = Enforce::FULL) const; 97 98 // Given package-root paths of ["hardware/interfaces", 99 // "vendor/<something>/interfaces"], package roots of 100 // ["android.hardware", "vendor.<something>.hardware"], and a 101 // FQName of "android.hardware.nfc@1.0::INfc, then getPackagePath() 102 // will return "hardware/interfaces/nfc/1.0" (if sanitized = false) 103 // or "hardware/interfaces/nfc/V1_0" (if sanitized = true). 104 status_t getPackagePath(const FQName& fqName, bool relative, bool sanitized, 105 std::string* path) const; 106 107 // Given package roots of ["android.hardware", 108 // "vendor.<something>.hardware"] and a FQName of 109 // "android.hardware.nfc@1.0::INfc, then getPackageRoot() will 110 // return "android.hardware". 111 status_t getPackageRoot(const FQName& fqName, std::string* root) const; 112 113 status_t getPackageInterfaceFiles( 114 const FQName &package, 115 std::vector<std::string> *fileNames) const; 116 117 status_t appendPackageInterfacesToVector( 118 const FQName &package, 119 std::vector<FQName> *packageInterfaces) const; 120 121 status_t isTypesOnlyPackage(const FQName& package, bool* result) const; 122 123 // Returns types which are imported/defined but not referenced in code 124 status_t addUnreferencedTypes(const std::vector<FQName>& packageInterfaces, 125 std::set<FQName>* unreferencedDefinitions, 126 std::set<FQName>* unreferencedImports) const; 127 128 // Enforce a set of restrictions on a set of packages. These include: 129 // - minor version upgrades 130 // "packages" contains names like "android.hardware.nfc@1.1". 131 // - hashing restrictions 132 status_t enforceRestrictionsOnPackage(const FQName& fqName, 133 Enforce enforcement = Enforce::FULL) const; 134 135 private: 136 static bool MakeParentHierarchy(const std::string &path); 137 138 enum class HashStatus { 139 ERROR, 140 UNFROZEN, 141 FROZEN, 142 CHANGED, // frozen but changed 143 }; 144 HashStatus checkHash(const FQName& fqName) const; 145 status_t getUnfrozenDependencies(const FQName& fqName, std::set<FQName>* result) const; 146 147 // indicates that packages in "android.hardware" will be looked up in hardware/interfaces 148 struct PackageRoot { 149 std::string path; // e.x. hardware/interfaces 150 FQName root; // e.x. android.hardware@0.0 151 }; 152 153 // nullptr if it doesn't exist 154 const PackageRoot* findPackageRoot(const FQName& fqName) const; 155 156 // Given package-root paths of ["hardware/interfaces", 157 // "vendor/<something>/interfaces"], package roots of 158 // ["android.hardware", "vendor.<something>.hardware"], and a 159 // FQName of "android.hardware.nfc@1.0::INfc, then getPackageRootPath() 160 // will return "hardware/interfaces". 161 status_t getPackageRootPath(const FQName& fqName, std::string* path) const; 162 163 // Given an FQName of "android.hardware.nfc@1.0::INfc", return 164 // "android/hardware/". 165 status_t convertPackageRootToPath(const FQName& fqName, std::string* path) const; 166 167 std::vector<PackageRoot> mPackageRoots; 168 std::string mRootPath; // root of android source tree (to locate package roots) 169 std::string mOutputPath; // root of output directory 170 std::string mDepFile; // location to write depfile 171 172 // hidl-gen options 173 bool mVerbose = false; 174 std::string mOwner; 175 176 // cache to parse(). 177 mutable std::map<FQName, AST *> mCache; 178 179 // cache to enforceRestrictionsOnPackage(). 180 mutable std::set<FQName> mPackagesEnforced; 181 182 mutable std::set<std::string> mReadFiles; 183 184 // Returns the given path if it is absolute, otherwise it returns 185 // the path relative to mRootPath 186 std::string makeAbsolute(const std::string& string) const; 187 188 // Rules of enforceRestrictionsOnPackage are listed below. 189 status_t enforceMinorVersionUprevs(const FQName& fqName, Enforce enforcement) const; 190 status_t enforceHashes(const FQName &fqName) const; 191 192 DISALLOW_COPY_AND_ASSIGN(Coordinator); 193 }; 194 195 } // namespace android 196 197 #endif // COORDINATOR_H_ 198