1 /* 2 * Copyright (C) 2015, 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 <iostream> 18 #include <string> 19 #include <vector> 20 21 #include <gtest/gtest.h> 22 23 #include "options.h" 24 25 using std::cerr; 26 using std::endl; 27 using std::string; 28 using std::unique_ptr; 29 using std::vector; 30 31 namespace android { 32 namespace aidl { 33 namespace { 34 35 const char kPreprocessCommandOutputFile[] = "output_file_name"; 36 const char kPreprocessCommandInput1[] = "input1"; 37 const char kPreprocessCommandInput2[] = "input2"; 38 const char kPreprocessCommandInput3[] = "input3"; 39 const char* kPreprocessCommand[] = { 40 "aidl", "--preprocess", 41 kPreprocessCommandOutputFile, 42 kPreprocessCommandInput1, 43 kPreprocessCommandInput2, 44 kPreprocessCommandInput3, 45 nullptr, 46 }; 47 48 const char kCompileCommandInput[] = "directory/ITool.aidl"; 49 const char kCompileCommandIncludePath[] = "-Iinclude_path"; 50 const char* kCompileJavaCommand[] = { 51 "aidl", 52 "-b", 53 kCompileCommandIncludePath, 54 kCompileCommandInput, 55 nullptr, 56 }; 57 const char kCompileCommandJavaOutput[] = "directory/ITool.java"; 58 59 const char kCompileDepFile[] = "-doutput.deps"; 60 const char kCompileCommandHeaderDir[] = "output/dir"; 61 const char kCompileCommandCppOutput[] = "some/file.cpp"; 62 const char* kCompileCppCommand[] = { 63 "aidl-cpp", 64 kCompileCommandIncludePath, 65 kCompileDepFile, 66 kCompileCommandInput, 67 kCompileCommandHeaderDir, 68 kCompileCommandCppOutput, 69 nullptr, 70 }; 71 72 template <typename T> 73 unique_ptr<T> GetOptions(const char* command[]) { 74 int argc = 0; 75 const char** command_part = command; 76 for (; *command_part; ++argc, ++command_part) {} 77 unique_ptr<T> options(T::Parse(argc, command)); 78 if (!options) { 79 cerr << "Failed to parse command line:"; 80 for (int i = 0; i < argc; ++i) { 81 cerr << " " << command[i]; 82 cerr << endl; 83 } 84 } 85 EXPECT_NE(options, nullptr) << "Failed to parse options!"; 86 return options; 87 } 88 89 } // namespace 90 91 TEST(JavaOptionsTests, ParsesPreprocess) { 92 unique_ptr<JavaOptions> options = GetOptions<JavaOptions>(kPreprocessCommand); 93 EXPECT_EQ(JavaOptions::PREPROCESS_AIDL, options->task); 94 EXPECT_EQ(false, options->fail_on_parcelable_); 95 EXPECT_EQ(0u, options->import_paths_.size()); 96 EXPECT_EQ(0u, options->preprocessed_files_.size()); 97 EXPECT_EQ(string{}, options->input_file_name_); 98 EXPECT_EQ(string{kPreprocessCommandOutputFile}, options->output_file_name_); 99 EXPECT_EQ(false, options->auto_dep_file_); 100 const vector<string> expected_input{kPreprocessCommandInput1, 101 kPreprocessCommandInput2, 102 kPreprocessCommandInput3}; 103 EXPECT_EQ(expected_input, options->files_to_preprocess_); 104 } 105 106 TEST(JavaOptionsTests, ParsesCompileJava) { 107 unique_ptr<JavaOptions> options = 108 GetOptions<JavaOptions>(kCompileJavaCommand); 109 EXPECT_EQ(JavaOptions::COMPILE_AIDL_TO_JAVA, options->task); 110 EXPECT_EQ(true, options->fail_on_parcelable_); 111 EXPECT_EQ(1u, options->import_paths_.size()); 112 EXPECT_EQ(0u, options->preprocessed_files_.size()); 113 EXPECT_EQ(string{kCompileCommandInput}, options->input_file_name_); 114 EXPECT_EQ(string{kCompileCommandJavaOutput}, options->output_file_name_); 115 EXPECT_EQ(false, options->auto_dep_file_); 116 } 117 118 TEST(CppOptionsTests, ParsesCompileCpp) { 119 unique_ptr<CppOptions> options = GetOptions<CppOptions>(kCompileCppCommand); 120 ASSERT_EQ(1u, options->import_paths_.size()); 121 EXPECT_EQ(string{kCompileCommandIncludePath}.substr(2), 122 options->import_paths_[0]); 123 EXPECT_EQ(string{kCompileDepFile}.substr(2), options->dep_file_name_); 124 EXPECT_EQ(kCompileCommandInput, options->InputFileName()); 125 EXPECT_EQ(kCompileCommandHeaderDir, options->OutputHeaderDir()); 126 EXPECT_EQ(kCompileCommandCppOutput, options->OutputCppFilePath()); 127 } 128 129 TEST(OptionsTests, EndsWith) { 130 EXPECT_TRUE(EndsWith("foo", "")); 131 EXPECT_TRUE(EndsWith("foo", "o")); 132 EXPECT_TRUE(EndsWith("foo", "foo")); 133 EXPECT_FALSE(EndsWith("foo", "fooo")); 134 EXPECT_FALSE(EndsWith("", "o")); 135 EXPECT_TRUE(EndsWith("", "")); 136 } 137 138 TEST(OptionsTests, ReplaceSuffix) { 139 struct test_case_t { 140 const char* input; 141 const char* old_suffix; 142 const char* new_suffix; 143 const char* result; 144 }; 145 const size_t kNumCases = 3; 146 test_case_t kTestInput[kNumCases] = { 147 {"foo.bar", "bar", "foo", "foo.foo"}, 148 {"whole", "whole", "new", "new"}, 149 {"", "", "", ""}, 150 }; 151 for (const auto& test_case : kTestInput) { 152 string mutated = test_case.input; 153 EXPECT_TRUE(ReplaceSuffix(test_case.old_suffix, 154 test_case.new_suffix, 155 &mutated)); 156 EXPECT_EQ(mutated, test_case.result); 157 } 158 } 159 160 } // namespace android 161 } // namespace aidl 162