AssembleVintf.cpp revision a59d2567783cad6f675d2fc1f2fcce4bce3e34e3
1/* 2 * Copyright (C) 2017 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#include <stdlib.h> 18#include <unistd.h> 19 20#include <fstream> 21#include <iostream> 22#include <unordered_map> 23#include <sstream> 24#include <string> 25 26#include <vintf/parse_string.h> 27#include <vintf/parse_xml.h> 28 29namespace android { 30namespace vintf { 31 32/** 33 * Slurps the device manifest file and add build time flag to it. 34 */ 35class AssembleVintf { 36public: 37 template<typename T> 38 static bool getFlag(const std::string& key, T* value) { 39 const char *envValue = getenv(key.c_str()); 40 if (envValue == NULL) { 41 std::cerr << "Required " << key << " flag." << std::endl; 42 return false; 43 } 44 45 if (!parse(envValue, value)) { 46 std::cerr << "Cannot parse " << envValue << "." << std::endl; 47 return false; 48 } 49 return true; 50 } 51 52 static bool assemble(std::basic_istream<char>& inFile, 53 std::basic_ostream<char>& outFile, 54 bool isMatrix) { 55 std::stringstream ss; 56 ss << inFile.rdbuf(); 57 std::string fileContent = ss.str(); 58 59 HalManifest halManifest; 60 if (!gHalManifestConverter(&halManifest, fileContent)) { 61 std::cerr << "Illformed HAL manifest: " << gHalManifestConverter.lastError() 62 << std::endl; 63 return false; 64 } 65 66 if (halManifest.mType == SchemaType::DEVICE) { 67 if (!getFlag("BOARD_SEPOLICY_VERS", &halManifest.device.mSepolicyVersion)) { 68 return false; 69 } 70 } 71 72 if (isMatrix) { 73 CompatibilityMatrix mat = halManifest.generateCompatibleMatrix(); 74 std::string error; 75 if (!halManifest.checkCompatibility(mat, &error)) { 76 std::cerr << "FATAL ERROR: cannot generate a compatible matrix: " 77 << error << std::endl; 78 } 79 outFile << "<!-- \n" 80 " Autogenerated skeleton compatibility matrix. \n" 81 " Use with caution. Modify it to suit your needs.\n" 82 " All HALs are set to optional.\n" 83 " Many entries other than HALs are zero-filled and\n" 84 " require human attention. \n" 85 "-->\n" 86 << gCompatibilityMatrixConverter(mat); 87 } else { 88 outFile << gHalManifestConverter(halManifest); 89 } 90 91 outFile.flush(); 92 93 return true; 94 } 95}; 96 97} // namespace vintf 98} // namespace android 99 100void help() { 101 std::cerr << 102 "assemble_vintf -h\n" 103 " Display this help text.\n" 104 "assemble_vintf -i <input file> [-o <output file>] [-m]\n" 105 " Fill in build-time flags into the given manifest.\n" 106 " If no designated output file, write to stdout.\n" 107 " If -m is set, a compatible compatibility matrix is\n" 108 " generated instead.\n"; 109} 110 111int main(int argc, char **argv) { 112 std::ifstream inFile; 113 std::ofstream outFile; 114 std::ostream* outFileRef = &std::cout; 115 bool isMatrix = false; 116 int res; 117 while((res = getopt(argc, argv, "hi:o:m")) >= 0) { 118 switch (res) { 119 case 'i': { 120 inFile.open(optarg); 121 if (!inFile.is_open()) { 122 std::cerr << "Failed to open " << optarg << std::endl; 123 return 1; 124 } 125 } break; 126 127 case 'o': { 128 outFile.open(optarg); 129 if (!outFile.is_open()) { 130 std::cerr << "Failed to open " << optarg << std::endl; 131 return 1; 132 } 133 outFileRef = &outFile; 134 } break; 135 136 case 'm': { 137 isMatrix = true; 138 } break; 139 140 case 'h': 141 default: { 142 help(); 143 return 1; 144 } break; 145 } 146 } 147 148 if (!inFile.is_open()) { 149 std::cerr << "Missing input file" << std::endl; 150 help(); 151 return 1; 152 } 153 154 return ::android::vintf::AssembleVintf::assemble(inFile, *outFileRef, isMatrix) 155 ? 0 : 1; 156} 157 158